ic 卡
This commit is contained in:
Generated
+9
@@ -0,0 +1,9 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<module type="JAVA_MODULE" version="4">
|
||||
<component name="NewModuleRootManager" inherit-compiler-output="true">
|
||||
<exclude-output />
|
||||
<content url="file://$MODULE_DIR$" />
|
||||
<orderEntry type="inheritedJdk" />
|
||||
<orderEntry type="sourceFolder" forTests="false" />
|
||||
</component>
|
||||
</module>
|
||||
Generated
+4
@@ -0,0 +1,4 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="Encoding" addBOMForNewFiles="with NO BOM" />
|
||||
</project>
|
||||
Generated
+6
@@ -0,0 +1,6 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="JavaScriptSettings">
|
||||
<option name="languageLevel" value="ES6" />
|
||||
</component>
|
||||
</project>
|
||||
Generated
+8
@@ -0,0 +1,8 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="ProjectModuleManager">
|
||||
<modules>
|
||||
<module fileurl="file://$PROJECT_DIR$/.idea/2019nCoV.iml" filepath="$PROJECT_DIR$/.idea/2019nCoV.iml" />
|
||||
</modules>
|
||||
</component>
|
||||
</project>
|
||||
Generated
+196
@@ -0,0 +1,196 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="ChangeListManager">
|
||||
<list default="true" id="379ce94e-8b54-4e06-8584-ec8f1cc09b79" name="Default Changelist" comment="" />
|
||||
<option name="EXCLUDED_CONVERTED_TO_IGNORED" value="true" />
|
||||
<option name="SHOW_DIALOG" value="false" />
|
||||
<option name="HIGHLIGHT_CONFLICTS" value="true" />
|
||||
<option name="HIGHLIGHT_NON_ACTIVE_CHANGELIST" value="false" />
|
||||
<option name="LAST_RESOLUTION" value="IGNORE" />
|
||||
</component>
|
||||
<component name="FileEditorManager">
|
||||
<leaf SIDE_TABS_SIZE_LIMIT_KEY="300">
|
||||
<file pinned="false" current-in-tab="true">
|
||||
<entry file="file://$PROJECT_DIR$/index.html">
|
||||
<provider selected="true" editor-type-id="text-editor">
|
||||
<state relative-caret-position="84">
|
||||
<caret line="4" column="33" selection-start-line="4" selection-start-column="33" selection-end-line="4" selection-end-column="33" />
|
||||
</state>
|
||||
</provider>
|
||||
</entry>
|
||||
</file>
|
||||
<file pinned="false" current-in-tab="false">
|
||||
<entry file="file://$PROJECT_DIR$/bkp.html">
|
||||
<provider selected="true" editor-type-id="text-editor">
|
||||
<state relative-caret-position="2079">
|
||||
<caret line="99" column="17" selection-start-line="99" selection-start-column="17" selection-end-line="99" selection-end-column="17" />
|
||||
</state>
|
||||
</provider>
|
||||
</entry>
|
||||
</file>
|
||||
</leaf>
|
||||
</component>
|
||||
<component name="FindInProjectRecents">
|
||||
<findStrings>
|
||||
<find>loader</find>
|
||||
<find>Controls</find>
|
||||
<find>OrbitControls</find>
|
||||
<find>camera</find>
|
||||
<find>initStats</find>
|
||||
<find>human</find>
|
||||
</findStrings>
|
||||
</component>
|
||||
<component name="IdeDocumentHistory">
|
||||
<option name="CHANGED_PATHS">
|
||||
<list>
|
||||
<option value="$PROJECT_DIR$/test1.html" />
|
||||
<option value="$PROJECT_DIR$/index.html" />
|
||||
</list>
|
||||
</option>
|
||||
</component>
|
||||
<component name="MacroExpansionManager">
|
||||
<option name="directoryName" value="YjjLpnxw" />
|
||||
</component>
|
||||
<component name="ProjectFrameBounds" extendedState="6">
|
||||
<option name="x" value="380" />
|
||||
<option name="y" value="134" />
|
||||
<option name="width" value="744" />
|
||||
<option name="height" value="456" />
|
||||
</component>
|
||||
<component name="ProjectView">
|
||||
<navigator proportions="" version="1">
|
||||
<foldersAlwaysOnTop value="true" />
|
||||
</navigator>
|
||||
<panes>
|
||||
<pane id="ProjectPane" />
|
||||
<pane id="PackagesPane" />
|
||||
<pane id="Scope" />
|
||||
</panes>
|
||||
</component>
|
||||
<component name="PropertiesComponent">
|
||||
<property name="WebServerToolWindowFactoryState" value="false" />
|
||||
<property name="go.gopath.indexing.explicitly.defined" value="true" />
|
||||
<property name="last_opened_file_path" value="$PROJECT_DIR$/../dragonfly" />
|
||||
<property name="nodejs_interpreter_path.stuck_in_default_project" value="undefined stuck path" />
|
||||
<property name="nodejs_npm_path_reset_for_default_project" value="true" />
|
||||
</component>
|
||||
<component name="RecentsManager">
|
||||
<key name="CopyFile.RECENT_KEYS">
|
||||
<recent name="C:\Users\Cheney\projects\js\2019nCoV" />
|
||||
</key>
|
||||
</component>
|
||||
<component name="RunDashboard">
|
||||
<option name="ruleStates">
|
||||
<list>
|
||||
<RuleState>
|
||||
<option name="name" value="ConfigurationTypeDashboardGroupingRule" />
|
||||
</RuleState>
|
||||
<RuleState>
|
||||
<option name="name" value="StatusDashboardGroupingRule" />
|
||||
</RuleState>
|
||||
</list>
|
||||
</option>
|
||||
</component>
|
||||
<component name="TaskManager">
|
||||
<task active="true" id="Default" summary="Default task">
|
||||
<changelist id="379ce94e-8b54-4e06-8584-ec8f1cc09b79" name="Default Changelist" comment="" />
|
||||
<created>1580969553492</created>
|
||||
<option name="number" value="Default" />
|
||||
<option name="presentableId" value="Default" />
|
||||
<updated>1580969553492</updated>
|
||||
<workItem from="1580969556504" duration="4692000" />
|
||||
<workItem from="1581142261901" duration="389000" />
|
||||
<workItem from="1581145978472" duration="229000" />
|
||||
</task>
|
||||
<servers />
|
||||
</component>
|
||||
<component name="TimeTrackingManager">
|
||||
<option name="totallyTimeSpent" value="5310000" />
|
||||
</component>
|
||||
<component name="ToolWindowManager">
|
||||
<frame x="-6" y="-6" width="1564" height="1093" extended-state="6" />
|
||||
<layout>
|
||||
<window_info active="true" content_ui="combo" id="Project" order="0" visible="true" weight="0.2563081" />
|
||||
<window_info id="Structure" order="1" side_tool="true" weight="0.25" />
|
||||
<window_info id="Designer" order="2" />
|
||||
<window_info id="UI Designer" order="3" />
|
||||
<window_info id="Favorites" order="4" side_tool="true" />
|
||||
<window_info anchor="bottom" id="Message" order="0" />
|
||||
<window_info anchor="bottom" id="Find" order="1" />
|
||||
<window_info anchor="bottom" id="Run" order="2" />
|
||||
<window_info anchor="bottom" id="Debug" order="3" weight="0.4" />
|
||||
<window_info anchor="bottom" id="Cvs" order="4" weight="0.25" />
|
||||
<window_info anchor="bottom" id="Inspection" order="5" weight="0.4" />
|
||||
<window_info anchor="bottom" id="TODO" order="6" />
|
||||
<window_info anchor="bottom" id="Docker" order="7" show_stripe_button="false" />
|
||||
<window_info anchor="bottom" id="Version Control" order="8" />
|
||||
<window_info anchor="bottom" id="Terminal" order="9" />
|
||||
<window_info anchor="bottom" id="Event Log" order="10" side_tool="true" />
|
||||
<window_info anchor="right" id="Commander" internal_type="SLIDING" order="0" type="SLIDING" weight="0.4" />
|
||||
<window_info anchor="right" id="Ant Build" order="1" weight="0.25" />
|
||||
<window_info anchor="right" content_ui="combo" id="Hierarchy" order="2" weight="0.25" />
|
||||
<window_info anchor="right" id="Palette" order="3" />
|
||||
<window_info anchor="right" id="Cargo" order="4" />
|
||||
<window_info anchor="right" id="Maven" order="5" />
|
||||
<window_info anchor="right" id="Palette	" order="6" />
|
||||
<window_info anchor="right" id="SciView" order="7" />
|
||||
</layout>
|
||||
</component>
|
||||
<component name="TypeScriptGeneratedFilesManager">
|
||||
<option name="version" value="1" />
|
||||
</component>
|
||||
<component name="editorHistoryManager">
|
||||
<entry file="file://$PROJECT_DIR$/three.js">
|
||||
<provider selected="true" editor-type-id="text-editor" />
|
||||
</entry>
|
||||
<entry file="file://$PROJECT_DIR$/ColladaLoader.js">
|
||||
<provider selected="true" editor-type-id="text-editor" />
|
||||
</entry>
|
||||
<entry file="file://$PROJECT_DIR$/stats.min.js">
|
||||
<provider selected="true" editor-type-id="text-editor" />
|
||||
</entry>
|
||||
<entry file="file://$PROJECT_DIR$/SVGRenderer.js">
|
||||
<provider selected="true" editor-type-id="text-editor" />
|
||||
</entry>
|
||||
<entry file="file://$PROJECT_DIR$/OrbitControls.js">
|
||||
<provider selected="true" editor-type-id="text-editor">
|
||||
<state relative-caret-position="-67">
|
||||
<caret line="15" selection-start-line="15" selection-end-line="15" />
|
||||
</state>
|
||||
</provider>
|
||||
</entry>
|
||||
<entry file="file://$PROJECT_DIR$/jquery.min.js">
|
||||
<provider selected="true" editor-type-id="text-editor" />
|
||||
</entry>
|
||||
<entry file="file://$PROJECT_DIR$/index.html">
|
||||
<provider selected="true" editor-type-id="text-editor">
|
||||
<state relative-caret-position="84">
|
||||
<caret line="4" column="33" selection-start-line="4" selection-start-column="33" selection-end-line="4" selection-end-column="33" />
|
||||
</state>
|
||||
</provider>
|
||||
</entry>
|
||||
<entry file="file://$PROJECT_DIR$/bkp.html">
|
||||
<provider selected="true" editor-type-id="text-editor">
|
||||
<state relative-caret-position="2079">
|
||||
<caret line="99" column="17" selection-start-line="99" selection-start-column="17" selection-end-line="99" selection-end-column="17" />
|
||||
</state>
|
||||
</provider>
|
||||
</entry>
|
||||
</component>
|
||||
<component name="masterDetails">
|
||||
<states>
|
||||
<state key="ProjectJDKs.UI">
|
||||
<settings>
|
||||
<last-edited>1.8</last-edited>
|
||||
<splitter-proportions>
|
||||
<option name="proportions">
|
||||
<list>
|
||||
<option value="0.2" />
|
||||
</list>
|
||||
</option>
|
||||
</splitter-proportions>
|
||||
</settings>
|
||||
</state>
|
||||
</states>
|
||||
</component>
|
||||
</project>
|
||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,508 @@
|
||||
/**
|
||||
* @author mrdoob / http://mrdoob.com/
|
||||
*/
|
||||
|
||||
THREE.SVGObject = function ( node ) {
|
||||
|
||||
THREE.Object3D.call( this );
|
||||
|
||||
this.node = node;
|
||||
|
||||
};
|
||||
|
||||
THREE.SVGObject.prototype = Object.create( THREE.Object3D.prototype );
|
||||
THREE.SVGObject.prototype.constructor = THREE.SVGObject;
|
||||
|
||||
THREE.SVGRenderer = function () {
|
||||
|
||||
console.log( 'THREE.SVGRenderer', THREE.REVISION );
|
||||
|
||||
var _this = this,
|
||||
_renderData, _elements, _lights,
|
||||
_projector = new THREE.Projector(),
|
||||
_svg = document.createElementNS( 'http://www.w3.org/2000/svg', 'svg' ),
|
||||
_svgWidth, _svgHeight, _svgWidthHalf, _svgHeightHalf,
|
||||
|
||||
_v1, _v2, _v3, _v4,
|
||||
|
||||
_clipBox = new THREE.Box2(),
|
||||
_elemBox = new THREE.Box2(),
|
||||
|
||||
_color = new THREE.Color(),
|
||||
_diffuseColor = new THREE.Color(),
|
||||
_ambientLight = new THREE.Color(),
|
||||
_directionalLights = new THREE.Color(),
|
||||
_pointLights = new THREE.Color(),
|
||||
_clearColor = new THREE.Color(),
|
||||
_clearAlpha = 1,
|
||||
|
||||
_vector3 = new THREE.Vector3(), // Needed for PointLight
|
||||
_centroid = new THREE.Vector3(),
|
||||
_normal = new THREE.Vector3(),
|
||||
_normalViewMatrix = new THREE.Matrix3(),
|
||||
|
||||
_viewMatrix = new THREE.Matrix4(),
|
||||
_viewProjectionMatrix = new THREE.Matrix4(),
|
||||
|
||||
_svgPathPool = [],
|
||||
_svgNode, _pathCount = 0,
|
||||
|
||||
_currentPath, _currentStyle,
|
||||
|
||||
_quality = 1, _precision = null;
|
||||
|
||||
this.domElement = _svg;
|
||||
|
||||
this.autoClear = true;
|
||||
this.sortObjects = true;
|
||||
this.sortElements = true;
|
||||
|
||||
this.info = {
|
||||
|
||||
render: {
|
||||
|
||||
vertices: 0,
|
||||
faces: 0
|
||||
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
this.setQuality = function( quality ) {
|
||||
|
||||
switch ( quality ) {
|
||||
|
||||
case "high": _quality = 1; break;
|
||||
case "low": _quality = 0; break;
|
||||
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
// WebGLRenderer compatibility
|
||||
|
||||
this.supportsVertexTextures = function () {};
|
||||
this.setFaceCulling = function () {};
|
||||
|
||||
this.setClearColor = function ( color, alpha ) {
|
||||
|
||||
_clearColor.set( color );
|
||||
_clearAlpha = alpha !== undefined ? alpha : 1;
|
||||
|
||||
};
|
||||
|
||||
this.setPixelRatio = function () {};
|
||||
|
||||
this.setSize = function( width, height ) {
|
||||
|
||||
_svgWidth = width; _svgHeight = height;
|
||||
_svgWidthHalf = _svgWidth / 2; _svgHeightHalf = _svgHeight / 2;
|
||||
|
||||
_svg.setAttribute( 'viewBox', ( - _svgWidthHalf ) + ' ' + ( - _svgHeightHalf ) + ' ' + _svgWidth + ' ' + _svgHeight );
|
||||
_svg.setAttribute( 'width', _svgWidth );
|
||||
_svg.setAttribute( 'height', _svgHeight );
|
||||
|
||||
_clipBox.min.set( - _svgWidthHalf, - _svgHeightHalf );
|
||||
_clipBox.max.set( _svgWidthHalf, _svgHeightHalf );
|
||||
|
||||
};
|
||||
|
||||
this.setPrecision = function ( precision ) {
|
||||
|
||||
_precision = precision;
|
||||
|
||||
};
|
||||
|
||||
function removeChildNodes() {
|
||||
|
||||
_pathCount = 0;
|
||||
|
||||
while ( _svg.childNodes.length > 0 ) {
|
||||
|
||||
_svg.removeChild( _svg.childNodes[ 0 ] );
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
function getSvgColor ( color, opacity ) {
|
||||
|
||||
var arg = Math.floor( color.r * 255 ) + ',' + Math.floor( color.g * 255 ) + ',' + Math.floor( color.b * 255 );
|
||||
|
||||
if ( opacity === undefined || opacity === 1 ) return 'rgb(' + arg + ')';
|
||||
|
||||
return 'rgb(' + arg + '); fill-opacity: ' + opacity;
|
||||
|
||||
}
|
||||
|
||||
function convert ( c ) {
|
||||
|
||||
return _precision !== null ? c.toFixed(_precision) : c;
|
||||
|
||||
}
|
||||
|
||||
this.clear = function () {
|
||||
|
||||
removeChildNodes();
|
||||
_svg.style.backgroundColor = getSvgColor( _clearColor, _clearAlpha );
|
||||
|
||||
};
|
||||
|
||||
this.render = function ( scene, camera ) {
|
||||
|
||||
if ( camera instanceof THREE.Camera === false ) {
|
||||
|
||||
console.error( 'THREE.SVGRenderer.render: camera is not an instance of THREE.Camera.' );
|
||||
return;
|
||||
|
||||
}
|
||||
|
||||
var background = scene.background;
|
||||
|
||||
if ( background && background.isColor ) {
|
||||
|
||||
removeChildNodes();
|
||||
_svg.style.backgroundColor = getSvgColor( background );
|
||||
|
||||
} else if ( this.autoClear === true ) {
|
||||
|
||||
this.clear();
|
||||
|
||||
}
|
||||
|
||||
_this.info.render.vertices = 0;
|
||||
_this.info.render.faces = 0;
|
||||
|
||||
_viewMatrix.copy( camera.matrixWorldInverse );
|
||||
_viewProjectionMatrix.multiplyMatrices( camera.projectionMatrix, _viewMatrix );
|
||||
|
||||
_renderData = _projector.projectScene( scene, camera, this.sortObjects, this.sortElements );
|
||||
_elements = _renderData.elements;
|
||||
_lights = _renderData.lights;
|
||||
|
||||
_normalViewMatrix.getNormalMatrix( camera.matrixWorldInverse );
|
||||
|
||||
calculateLights( _lights );
|
||||
|
||||
// reset accumulated path
|
||||
|
||||
_currentPath = '';
|
||||
_currentStyle = '';
|
||||
|
||||
for ( var e = 0, el = _elements.length; e < el; e ++ ) {
|
||||
|
||||
var element = _elements[ e ];
|
||||
var material = element.material;
|
||||
|
||||
if ( material === undefined || material.opacity === 0 ) continue;
|
||||
|
||||
_elemBox.makeEmpty();
|
||||
|
||||
if ( element instanceof THREE.RenderableSprite ) {
|
||||
|
||||
_v1 = element;
|
||||
_v1.x *= _svgWidthHalf; _v1.y *= - _svgHeightHalf;
|
||||
|
||||
renderSprite( _v1, element, material );
|
||||
|
||||
} else if ( element instanceof THREE.RenderableLine ) {
|
||||
|
||||
_v1 = element.v1; _v2 = element.v2;
|
||||
|
||||
_v1.positionScreen.x *= _svgWidthHalf; _v1.positionScreen.y *= - _svgHeightHalf;
|
||||
_v2.positionScreen.x *= _svgWidthHalf; _v2.positionScreen.y *= - _svgHeightHalf;
|
||||
|
||||
_elemBox.setFromPoints( [ _v1.positionScreen, _v2.positionScreen ] );
|
||||
|
||||
if ( _clipBox.intersectsBox( _elemBox ) === true ) {
|
||||
|
||||
renderLine( _v1, _v2, element, material );
|
||||
|
||||
}
|
||||
|
||||
} else if ( element instanceof THREE.RenderableFace ) {
|
||||
|
||||
_v1 = element.v1; _v2 = element.v2; _v3 = element.v3;
|
||||
|
||||
if ( _v1.positionScreen.z < - 1 || _v1.positionScreen.z > 1 ) continue;
|
||||
if ( _v2.positionScreen.z < - 1 || _v2.positionScreen.z > 1 ) continue;
|
||||
if ( _v3.positionScreen.z < - 1 || _v3.positionScreen.z > 1 ) continue;
|
||||
|
||||
_v1.positionScreen.x *= _svgWidthHalf; _v1.positionScreen.y *= - _svgHeightHalf;
|
||||
_v2.positionScreen.x *= _svgWidthHalf; _v2.positionScreen.y *= - _svgHeightHalf;
|
||||
_v3.positionScreen.x *= _svgWidthHalf; _v3.positionScreen.y *= - _svgHeightHalf;
|
||||
|
||||
_elemBox.setFromPoints( [
|
||||
_v1.positionScreen,
|
||||
_v2.positionScreen,
|
||||
_v3.positionScreen
|
||||
] );
|
||||
|
||||
if ( _clipBox.intersectsBox( _elemBox ) === true ) {
|
||||
|
||||
renderFace3( _v1, _v2, _v3, element, material );
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
flushPath(); // just to flush last svg:path
|
||||
|
||||
scene.traverseVisible( function ( object ) {
|
||||
|
||||
if ( object instanceof THREE.SVGObject ) {
|
||||
|
||||
_vector3.setFromMatrixPosition( object.matrixWorld );
|
||||
_vector3.applyMatrix4( _viewProjectionMatrix );
|
||||
|
||||
var x = _vector3.x * _svgWidthHalf;
|
||||
var y = - _vector3.y * _svgHeightHalf;
|
||||
|
||||
var node = object.node;
|
||||
node.setAttribute( 'transform', 'translate(' + x + ',' + y + ')' );
|
||||
|
||||
_svg.appendChild( node );
|
||||
|
||||
}
|
||||
|
||||
} );
|
||||
|
||||
};
|
||||
|
||||
function calculateLights( lights ) {
|
||||
|
||||
_ambientLight.setRGB( 0, 0, 0 );
|
||||
_directionalLights.setRGB( 0, 0, 0 );
|
||||
_pointLights.setRGB( 0, 0, 0 );
|
||||
|
||||
for ( var l = 0, ll = lights.length; l < ll; l ++ ) {
|
||||
|
||||
var light = lights[ l ];
|
||||
var lightColor = light.color;
|
||||
|
||||
if ( light instanceof THREE.AmbientLight ) {
|
||||
|
||||
_ambientLight.r += lightColor.r;
|
||||
_ambientLight.g += lightColor.g;
|
||||
_ambientLight.b += lightColor.b;
|
||||
|
||||
} else if ( light instanceof THREE.DirectionalLight ) {
|
||||
|
||||
_directionalLights.r += lightColor.r;
|
||||
_directionalLights.g += lightColor.g;
|
||||
_directionalLights.b += lightColor.b;
|
||||
|
||||
} else if ( light instanceof THREE.PointLight ) {
|
||||
|
||||
_pointLights.r += lightColor.r;
|
||||
_pointLights.g += lightColor.g;
|
||||
_pointLights.b += lightColor.b;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
function calculateLight( lights, position, normal, color ) {
|
||||
|
||||
for ( var l = 0, ll = lights.length; l < ll; l ++ ) {
|
||||
|
||||
var light = lights[ l ];
|
||||
var lightColor = light.color;
|
||||
|
||||
if ( light instanceof THREE.DirectionalLight ) {
|
||||
|
||||
var lightPosition = _vector3.setFromMatrixPosition( light.matrixWorld ).normalize();
|
||||
|
||||
var amount = normal.dot( lightPosition );
|
||||
|
||||
if ( amount <= 0 ) continue;
|
||||
|
||||
amount *= light.intensity;
|
||||
|
||||
color.r += lightColor.r * amount;
|
||||
color.g += lightColor.g * amount;
|
||||
color.b += lightColor.b * amount;
|
||||
|
||||
} else if ( light instanceof THREE.PointLight ) {
|
||||
|
||||
var lightPosition = _vector3.setFromMatrixPosition( light.matrixWorld );
|
||||
|
||||
var amount = normal.dot( _vector3.subVectors( lightPosition, position ).normalize() );
|
||||
|
||||
if ( amount <= 0 ) continue;
|
||||
|
||||
amount *= light.distance == 0 ? 1 : 1 - Math.min( position.distanceTo( lightPosition ) / light.distance, 1 );
|
||||
|
||||
if ( amount == 0 ) continue;
|
||||
|
||||
amount *= light.intensity;
|
||||
|
||||
color.r += lightColor.r * amount;
|
||||
color.g += lightColor.g * amount;
|
||||
color.b += lightColor.b * amount;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
function renderSprite( v1, element, material ) {
|
||||
|
||||
var scaleX = element.scale.x * _svgWidthHalf;
|
||||
var scaleY = element.scale.y * _svgHeightHalf;
|
||||
|
||||
if ( material.isPointsMaterial ) {
|
||||
scaleX *= material.size;
|
||||
scaleY *= material.size;
|
||||
}
|
||||
|
||||
var path = 'M' + convert( v1.x - scaleX * 0.5 ) + ',' + convert( v1.y - scaleY * 0.5 ) + 'h' + convert( scaleX ) + 'v' + convert( scaleY ) + 'h' + convert(-scaleX) + 'z';
|
||||
var style = "";
|
||||
|
||||
if ( material.isSpriteMaterial || material.isPointsMaterial ) {
|
||||
|
||||
style = 'fill:' + getSvgColor( material.color, material.opacity );
|
||||
|
||||
}
|
||||
|
||||
addPath( style, path );
|
||||
|
||||
}
|
||||
|
||||
function renderLine( v1, v2, element, material ) {
|
||||
|
||||
var path = 'M' + convert( v1.positionScreen.x ) + ',' + convert( v1.positionScreen.y ) + 'L' + convert( v2.positionScreen.x ) + ',' + convert( v2.positionScreen.y );
|
||||
|
||||
if ( material.isLineBasicMaterial ) {
|
||||
|
||||
var style = 'fill:none;stroke:' + getSvgColor( material.color, material.opacity ) + ';stroke-width:' + material.linewidth + ';stroke-linecap:' + material.linecap;
|
||||
|
||||
if ( material.isLineDashedMaterial ) {
|
||||
|
||||
style = style + ';stroke-dasharray:' + material.dashSize + "," + material.gapSize;
|
||||
|
||||
}
|
||||
|
||||
addPath( style, path );
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
function renderFace3( v1, v2, v3, element, material ) {
|
||||
|
||||
_this.info.render.vertices += 3;
|
||||
_this.info.render.faces ++;
|
||||
|
||||
var path = 'M' + convert( v1.positionScreen.x ) + ',' + convert( v1.positionScreen.y ) + 'L' + convert( v2.positionScreen.x ) + ',' + convert( v2.positionScreen.y ) + 'L' + convert( v3.positionScreen.x ) + ',' + convert( v3.positionScreen.y ) + 'z';
|
||||
var style = '';
|
||||
|
||||
if ( material instanceof THREE.MeshBasicMaterial ) {
|
||||
|
||||
_color.copy( material.color );
|
||||
|
||||
if ( material.vertexColors === THREE.FaceColors ) {
|
||||
|
||||
_color.multiply( element.color );
|
||||
|
||||
}
|
||||
|
||||
} else if ( material instanceof THREE.MeshLambertMaterial || material instanceof THREE.MeshPhongMaterial ) {
|
||||
|
||||
_diffuseColor.copy( material.color );
|
||||
|
||||
if ( material.vertexColors === THREE.FaceColors ) {
|
||||
|
||||
_diffuseColor.multiply( element.color );
|
||||
|
||||
}
|
||||
|
||||
_color.copy( _ambientLight );
|
||||
|
||||
_centroid.copy( v1.positionWorld ).add( v2.positionWorld ).add( v3.positionWorld ).divideScalar( 3 );
|
||||
|
||||
calculateLight( _lights, _centroid, element.normalModel, _color );
|
||||
|
||||
_color.multiply( _diffuseColor ).add( material.emissive );
|
||||
|
||||
} else if ( material instanceof THREE.MeshNormalMaterial ) {
|
||||
|
||||
_normal.copy( element.normalModel ).applyMatrix3( _normalViewMatrix );
|
||||
|
||||
_color.setRGB( _normal.x, _normal.y, _normal.z ).multiplyScalar( 0.5 ).addScalar( 0.5 );
|
||||
|
||||
}
|
||||
|
||||
if ( material.wireframe ) {
|
||||
|
||||
style = 'fill:none;stroke:' + getSvgColor( _color, material.opacity ) + ';stroke-width:' + material.wireframeLinewidth + ';stroke-linecap:' + material.wireframeLinecap + ';stroke-linejoin:' + material.wireframeLinejoin;
|
||||
|
||||
} else {
|
||||
|
||||
style = 'fill:' + getSvgColor( _color, material.opacity );
|
||||
|
||||
}
|
||||
|
||||
addPath( style, path );
|
||||
|
||||
}
|
||||
|
||||
function addPath ( style, path ) {
|
||||
|
||||
if ( _currentStyle === style ) {
|
||||
|
||||
_currentPath += path
|
||||
|
||||
} else {
|
||||
|
||||
flushPath();
|
||||
|
||||
_currentStyle = style;
|
||||
_currentPath = path;
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
function flushPath() {
|
||||
|
||||
if ( _currentPath ) {
|
||||
|
||||
_svgNode = getPathNode( _pathCount ++ );
|
||||
_svgNode.setAttribute( 'd', _currentPath );
|
||||
_svgNode.setAttribute( 'style', _currentStyle );
|
||||
_svg.appendChild( _svgNode );
|
||||
|
||||
}
|
||||
|
||||
_currentPath = '';
|
||||
_currentStyle = '';
|
||||
|
||||
}
|
||||
|
||||
function getPathNode( id ) {
|
||||
|
||||
if ( _svgPathPool[ id ] == null ) {
|
||||
|
||||
_svgPathPool[ id ] = document.createElementNS( 'http://www.w3.org/2000/svg', 'path' );
|
||||
|
||||
if ( _quality == 0 ) {
|
||||
|
||||
_svgPathPool[ id ].setAttribute( 'shape-rendering', 'crispEdges' ); //optimizeSpeed
|
||||
|
||||
}
|
||||
|
||||
return _svgPathPool[ id ];
|
||||
|
||||
}
|
||||
|
||||
return _svgPathPool[ id ];
|
||||
|
||||
}
|
||||
|
||||
};
|
||||
@@ -0,0 +1,136 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>2019nCov draw by Cheney</title>
|
||||
<style type="text/css">
|
||||
body {
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
canvas {
|
||||
width: 100%;
|
||||
height: 100%
|
||||
}
|
||||
</style>
|
||||
<script src="./three.js" type="text/javascript"></script>
|
||||
<script src="./ColladaLoader.js" type="text/javascript"></script>
|
||||
<script src="./OrbitControls.js" type="text/javascript"></script>
|
||||
<script type="text/javascript">
|
||||
var scene, camera, renderer, daeModel;
|
||||
// 获得可见区域宽度
|
||||
var width = document.documentElement.clientWidth;
|
||||
// 获得可见区域的高度
|
||||
var height = document.documentElement.clientHeight;
|
||||
//初始化场景
|
||||
function initScene() {
|
||||
scene = new THREE.Scene();
|
||||
}
|
||||
|
||||
//初始化摄像机
|
||||
function initcamera() {
|
||||
aspect = width / height;
|
||||
D = 8;
|
||||
camera = new THREE.OrthographicCamera(-D * aspect, D * aspect, D, -D, 1, 1000);
|
||||
//camera = new THREE.PerspectiveCamera(75, window.innerWidth/window.innerHeight,0.1,200)
|
||||
camera.position.set(300, -300, 300);
|
||||
camera.lookAt(new THREE.Vector3(0, 0, 0));
|
||||
camera.up.x = 0;
|
||||
camera.up.y = 0;
|
||||
camera.up.z = 1;
|
||||
//camera.rotation.z = 1 / 6 * Math.PI;
|
||||
//camera.rotation.z = 5/6*Math.PI;
|
||||
}
|
||||
|
||||
function initthree() {
|
||||
renderer = new THREE.WebGLRenderer();
|
||||
renderer.setSize(width, height);
|
||||
renderer.setClearColor(0xffffff);
|
||||
document.body.appendChild(renderer.domElement);
|
||||
/*
|
||||
var spotLight = new THREE.SpotLight( 0xffffff );
|
||||
spotLight.position.set( 100, 1000, 100 );
|
||||
|
||||
spotLight.castShadow = true;
|
||||
|
||||
spotLight.shadow.mapSize.width = 1024;
|
||||
spotLight.shadow.mapSize.height = 1024;
|
||||
|
||||
spotLight.shadow.camera.near = 500;
|
||||
spotLight.shadow.camera.far = 4000;
|
||||
spotLight.shadow.camera.fov = 30;
|
||||
|
||||
scene.add( spotLight );
|
||||
*/
|
||||
}
|
||||
|
||||
function initlight() {
|
||||
var light = new THREE.DirectionalLight(0xffffff, 2);
|
||||
light.position.set(300, -300, 200);
|
||||
scene.add(light);
|
||||
|
||||
|
||||
var ambientLight = new THREE.AmbientLight( 0xffffff, 0.2 );
|
||||
scene.add( ambientLight );
|
||||
|
||||
var pointLight = new THREE.PointLight( 0xffffff, 0.8 );
|
||||
camera.add( pointLight );
|
||||
}
|
||||
|
||||
function LoadModel() {
|
||||
var loader = new THREE.ColladaLoader();
|
||||
loader.load("./model.dae", function (collada) {
|
||||
|
||||
console.log("collada", collada)
|
||||
|
||||
daeModel = collada.scene;
|
||||
daeModel.scale.set(5, 5, 5);
|
||||
daeModel.position.set(0, 0, 0);
|
||||
scene.add(daeModel);
|
||||
//参考坐标轴
|
||||
var axisHelper = new THREE.AxisHelper(500);
|
||||
scene.add(axisHelper);
|
||||
},
|
||||
function (xhr) {
|
||||
console.log((xhr.loaded / xhr.total * 100) + "% loaded");
|
||||
});
|
||||
}
|
||||
|
||||
//初始化渲染器
|
||||
function render() {
|
||||
requestAnimationFrame(render);
|
||||
|
||||
renderer.clear();
|
||||
|
||||
renderer.render(scene, camera);
|
||||
//if( daeModel ){
|
||||
// daeModel.rotation.z++;
|
||||
//}
|
||||
}
|
||||
|
||||
var Controls;
|
||||
|
||||
// 初始化控制器
|
||||
function initControls() {
|
||||
Controls = new THREE.OrbitControls(camera);
|
||||
}
|
||||
|
||||
function startGame() {
|
||||
console.log('Load Model started...');
|
||||
initScene();
|
||||
initcamera();
|
||||
initthree();
|
||||
initlight();
|
||||
LoadModel();
|
||||
render();
|
||||
initControls();
|
||||
|
||||
}
|
||||
|
||||
|
||||
</script>
|
||||
</head>
|
||||
<body onload="startGame()" onresize="startGame()">
|
||||
</body>
|
||||
|
||||
</html>
|
||||
@@ -0,0 +1,217 @@
|
||||
<!DOCTYPE html>
|
||||
<html>
|
||||
|
||||
<head>
|
||||
<title>2019nCov draw by Cheney</title>
|
||||
<script type="text/javascript" src="./three.js"></script>
|
||||
<script src="./ColladaLoader.js" type="text/javascript"></script>
|
||||
<script src="./OrbitControls.js" type="text/javascript"></script>
|
||||
<script src="./jquery.min.js"></script>
|
||||
<script type="text/javascript" src="./stats.min.js"></script>
|
||||
<script type="text/javascript" src="./SVGRenderer.js"></script>
|
||||
|
||||
<script id="vertexShader" type="x-shader/x-vertex">
|
||||
uniform vec3 viewVector;
|
||||
uniform float c;
|
||||
uniform float p;
|
||||
varying float intensity;
|
||||
void main()
|
||||
{
|
||||
vec3 vNormal = normalize( normalMatrix * normal );
|
||||
vec3 vNormel = normalize( normalMatrix * viewVector );
|
||||
intensity = pow( c - dot(vNormal, vNormel), p );
|
||||
|
||||
gl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );
|
||||
}
|
||||
</script>
|
||||
|
||||
<!-- fragment shader a.k.a. pixel shader -->
|
||||
<script id="fragmentShader" type="x-shader/x-vertex">
|
||||
uniform vec3 glowColor;
|
||||
varying float intensity;
|
||||
void main()
|
||||
{
|
||||
vec3 glow = glowColor * intensity;
|
||||
gl_FragColor = vec4( glow, 1.0 );
|
||||
}
|
||||
</script>
|
||||
<style>
|
||||
body {
|
||||
/* set margin to 0 and overflow to hidden, to go fullscreen */
|
||||
|
||||
margin: 0;
|
||||
overflow: hidden;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
|
||||
<div id="Stats-output">
|
||||
</div>
|
||||
<!-- Div which will hold the Output -->
|
||||
<div id="WebGL-output">
|
||||
</div>
|
||||
|
||||
<!-- Javascript code that runs our Three.js examples -->
|
||||
<script type="text/javascript">
|
||||
// once everything is loaded, we run our Three.js stuff.
|
||||
$(function () {
|
||||
var mouseX = 0, mouseY = 0;
|
||||
var human;
|
||||
camstep = 0;
|
||||
|
||||
var stats = initStats();
|
||||
|
||||
// create a scene, that will hold all our elements such as objects, cameras and lights.
|
||||
var scene = new THREE.Scene();
|
||||
|
||||
// create a camera, which defines where we're looking at.
|
||||
var camera = new THREE.PerspectiveCamera(45, window.innerWidth / window.innerHeight, 0.1, 1000);
|
||||
|
||||
// create a render and set the size
|
||||
var renderer = new THREE.WebGLRenderer({antialias: true, alpha: true});
|
||||
|
||||
renderer.setClearColor(0x000000, 1.0);
|
||||
renderer.setSize(window.innerWidth, window.innerHeight);
|
||||
renderer.shadowMapEnabled = true;
|
||||
renderer.shadowMapType = THREE.PCFShadowMap;
|
||||
|
||||
|
||||
materialCameraPosition = camera.position.clone();
|
||||
materialCameraPosition.z += 10;
|
||||
|
||||
// position and point the camera to the center of the scene
|
||||
camera.position.x = -10;
|
||||
camera.position.y = 0;
|
||||
camera.position.z = 15;
|
||||
lookAt = scene.position;
|
||||
lookAt.y = 15;
|
||||
camera.lookAt(lookAt);
|
||||
|
||||
// add subtle ambient lighting
|
||||
var ambientLight = new THREE.AmbientLight(0x0c0c0c);
|
||||
//scene.add(ambientLight);
|
||||
|
||||
|
||||
// add the output of the renderer to the html element
|
||||
$("#WebGL-output").append(renderer.domElement);
|
||||
|
||||
var customMaterial = new THREE.ShaderMaterial(
|
||||
{
|
||||
uniforms: {
|
||||
"c": { type: "f", value: 1.0 },
|
||||
"p": { type: "f", value: 3 },
|
||||
glowColor: { type: "c", value: new THREE.Color(0x84ccff) },
|
||||
viewVector: { type: "v3", value: materialCameraPosition }
|
||||
},
|
||||
vertexShader: document.getElementById('vertexShader').textContent,
|
||||
fragmentShader: document.getElementById('fragmentShader').textContent,
|
||||
side: THREE.FrontSide,
|
||||
blending: THREE.AdditiveBlending,
|
||||
transparent: true,
|
||||
opacity: 0.1,
|
||||
depthWrite: false
|
||||
});
|
||||
|
||||
var manager = new THREE.LoadingManager();
|
||||
manager.onProgress = function (item, loaded, total) {
|
||||
console.log(item, loaded, total);
|
||||
};
|
||||
// var loader = new THREE.OBJLoader(manager);
|
||||
// loader.load('body_anatomy3.obj', function (object) {
|
||||
// console.log(object);
|
||||
// object.traverse(function (child) {
|
||||
// if (child instanceof THREE.Mesh) {
|
||||
// console.log(child);
|
||||
// child.material = customMaterial;
|
||||
// }
|
||||
// });
|
||||
// object.position.y = 4;
|
||||
// object.scale.x = 0.01;
|
||||
// object.scale.y = 0.01;
|
||||
// object.scale.z = 0.01;
|
||||
// human = object;
|
||||
// scene.add(human);
|
||||
// });
|
||||
var loader = new THREE.ColladaLoader();
|
||||
loader.load("./model.dae", function (collada) {
|
||||
|
||||
console.log("collada", collada)
|
||||
collada.scene.children[0].material = customMaterial;
|
||||
daeModel = collada.scene;
|
||||
daeModel.scale.set(5, 5, 5);
|
||||
daeModel.position.set(0, 0, 0);
|
||||
scene.add(daeModel);
|
||||
//参考坐标轴
|
||||
var axisHelper = new THREE.AxisHelper(500);
|
||||
scene.add(axisHelper);
|
||||
},
|
||||
function (xhr) {
|
||||
console.log((xhr.loaded / xhr.total * 100) + "% loaded");
|
||||
});
|
||||
|
||||
// call the render function
|
||||
var step = 0;
|
||||
render();
|
||||
|
||||
function render() {
|
||||
stats.update();
|
||||
|
||||
// camstep += 0.02;
|
||||
//
|
||||
// camera.position.x = -20 * (Math.cos(camstep));
|
||||
// camera.position.z = (20 * (Math.sin(camstep)));
|
||||
// camera.position.y = 20;
|
||||
|
||||
camera.lookAt(lookAt);
|
||||
//
|
||||
// if (human) {
|
||||
// //human.rotation.y += 0.02;
|
||||
// materialCameraPosition = camera.position.clone();
|
||||
// materialCameraPosition.z += 10;
|
||||
// human.traverse(function (child) {
|
||||
// if (child instanceof THREE.Mesh) {
|
||||
// //console.log(child.material.uniforms.viewVector);
|
||||
// child.material.uniforms.viewVector.value =
|
||||
// new THREE.Vector3().subVectors(camera.position, human.position);
|
||||
// }
|
||||
// });
|
||||
// }
|
||||
|
||||
//sphere.material.uniforms.viewVector.value = new THREE.Vector3().subVectors(camera.position, sphere.position);
|
||||
|
||||
// render using requestAnimationFrame
|
||||
requestAnimationFrame(render);
|
||||
renderer.render(scene, camera);
|
||||
}
|
||||
|
||||
function initStats() {
|
||||
|
||||
var stats = new Stats();
|
||||
|
||||
stats.setMode(0); // 0: fps, 1: ms
|
||||
|
||||
// Align top-left
|
||||
stats.domElement.style.position = 'absolute';
|
||||
stats.domElement.style.left = '0px';
|
||||
stats.domElement.style.top = '0px';
|
||||
|
||||
$("#Stats-output").append(stats.domElement);
|
||||
|
||||
return stats;
|
||||
}
|
||||
|
||||
var Controls;
|
||||
|
||||
// 初始化控制器
|
||||
function initControls() {
|
||||
Controls = new THREE.OrbitControls(camera);
|
||||
}
|
||||
initControls()
|
||||
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
Vendored
+4
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
Vendored
+5
@@ -0,0 +1,5 @@
|
||||
// stats.js - http://github.com/mrdoob/stats.js
|
||||
var Stats=function(){function h(a){c.appendChild(a.dom);return a}function k(a){for(var d=0;d<c.children.length;d++)c.children[d].style.display=d===a?"block":"none";l=a}var l=0,c=document.createElement("div");c.style.cssText="position:fixed;top:0;left:0;cursor:pointer;opacity:0.9;z-index:10000";c.addEventListener("click",function(a){a.preventDefault();k(++l%c.children.length)},!1);var g=(performance||Date).now(),e=g,a=0,r=h(new Stats.Panel("FPS","#0ff","#002")),f=h(new Stats.Panel("MS","#0f0","#020"));
|
||||
if(self.performance&&self.performance.memory)var t=h(new Stats.Panel("MB","#f08","#201"));k(0);return{REVISION:16,dom:c,addPanel:h,showPanel:k,begin:function(){g=(performance||Date).now()},end:function(){a++;var c=(performance||Date).now();f.update(c-g,200);if(c>e+1E3&&(r.update(1E3*a/(c-e),100),e=c,a=0,t)){var d=performance.memory;t.update(d.usedJSHeapSize/1048576,d.jsHeapSizeLimit/1048576)}return c},update:function(){g=this.end()},domElement:c,setMode:k}};
|
||||
Stats.Panel=function(h,k,l){var c=Infinity,g=0,e=Math.round,a=e(window.devicePixelRatio||1),r=80*a,f=48*a,t=3*a,u=2*a,d=3*a,m=15*a,n=74*a,p=30*a,q=document.createElement("canvas");q.width=r;q.height=f;q.style.cssText="width:80px;height:48px";var b=q.getContext("2d");b.font="bold "+9*a+"px Helvetica,Arial,sans-serif";b.textBaseline="top";b.fillStyle=l;b.fillRect(0,0,r,f);b.fillStyle=k;b.fillText(h,t,u);b.fillRect(d,m,n,p);b.fillStyle=l;b.globalAlpha=.9;b.fillRect(d,m,n,p);return{dom:q,update:function(f,
|
||||
v){c=Math.min(c,f);g=Math.max(g,f);b.fillStyle=l;b.globalAlpha=1;b.fillRect(0,0,r,m);b.fillStyle=k;b.fillText(e(f)+" "+h+" ("+e(c)+"-"+e(g)+")",t,u);b.drawImage(q,d+a,m,n-a,p,d,m,n-a,p);b.fillRect(d+n-a,m,a,p);b.fillStyle=l;b.globalAlpha=.9;b.fillRect(d+n-a,m,a,e((1-f/v)*p))}}};"object"===typeof module&&(module.exports=Stats);
|
||||
+48034
File diff suppressed because one or more lines are too long
@@ -0,0 +1,14 @@
|
||||
ASN.1 JavaScript decoder Copyright (c) 2008-2020 Lapo Luchini <lapo@lapo.it>
|
||||
|
||||
Permission to use, copy, modify, and/or distribute this software for any
|
||||
purpose with or without fee is hereby granted, provided that the above
|
||||
copyright notice and this permission notice appear in all copies.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
@@ -0,0 +1,75 @@
|
||||
asn1js
|
||||
======
|
||||
|
||||
asn1js is a JavaScript generic ASN.1 parser/decoder that can decode any valid ASN.1 DER or BER structures.
|
||||
|
||||
An example page that can decode Base64-encoded (raw base64, PEM armoring and `begin-base64` are recognized) or Hex-encoded (or local files with some browsers) is included and can be used both [online on the official website](https://lapo.it/asn1js/) or [offline (ZIP file)](https://lapo.it/asn1js/asn1js.zip).
|
||||
|
||||
Usage with `npm` / `yarn`
|
||||
-------------------------
|
||||
|
||||
This package can be installed with either npm or yarn via the following commands:
|
||||
|
||||
```sh
|
||||
npm install @lapo/asn1js
|
||||
# or with yarn
|
||||
yarn add @lapo/asn1js
|
||||
```
|
||||
|
||||
Assuming a standard javascript bundler is setup you can import it like so:
|
||||
|
||||
```js
|
||||
const ASN1 = require('@lapo/asn1js');
|
||||
// or with ES modules
|
||||
import ASN1 from '@lapo/asn1js';
|
||||
```
|
||||
|
||||
A submodule of this package can also be imported:
|
||||
|
||||
```js
|
||||
const Hex = require('@lapo/asn1js/hex');
|
||||
// or with ES modules
|
||||
import Hex from '@lapo/asn1js/hex';
|
||||
```
|
||||
|
||||
Usage with RequireJS
|
||||
--------------------
|
||||
|
||||
Can be [tested on JSFiddle](https://jsfiddle.net/lapo/tmdq35ug/).
|
||||
|
||||
```html
|
||||
<script type="text/javascript" src="https://unpkg.com/requirejs/require.js"></script>
|
||||
<script>
|
||||
require([
|
||||
'https://unpkg.com/@lapo/asn1js/asn1.js',
|
||||
'https://unpkg.com/@lapo/asn1js/hex.js'
|
||||
], function(ASN1, Hex) {
|
||||
document.body.innerText = ASN1.decode(Hex.decode('06032B6570')).content();
|
||||
});
|
||||
</script>
|
||||
```
|
||||
|
||||
ISC license
|
||||
-----------
|
||||
|
||||
ASN.1 JavaScript decoder Copyright (c) 2008-2020 Lapo Luchini <lapo@lapo.it>
|
||||
|
||||
Permission to use, copy, modify, and/or distribute this software for any purpose with or without fee is hereby granted, provided that the above copyright notice and this permission notice appear in all copies.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
credits
|
||||
-------
|
||||
|
||||
- OBJECT IDENTIFIER values are recognized using data taken from Peter Gutmann's [dumpasn1](https://www.cs.auckland.ac.nz/~pgut001/#standards) program.
|
||||
- BMPString support added by [Felipe Gasper](https://github.com/FGasper)
|
||||
- extended tag support added by [Péter Budai](https://www.peterbudai.eu/)
|
||||
- patches by [Gergely Nagy](https://github.com/ngg)
|
||||
|
||||
links
|
||||
-----
|
||||
|
||||
- [official website](https://lapo.it/asn1js/)
|
||||
- [InDefero tracker](http://idf.lapo.it/p/asn1js/)
|
||||
- [GitHub mirror](https://github.com/lapo-luchini/asn1js)
|
||||
- [Ohloh code stats](https://www.openhub.net/p/asn1js)
|
||||
@@ -0,0 +1,550 @@
|
||||
// ASN.1 JavaScript decoder
|
||||
// Copyright (c) 2008-2020 Lapo Luchini <lapo@lapo.it>
|
||||
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
(typeof define != 'undefined' ? define : function (factory) { 'use strict';
|
||||
if (typeof module == 'object') module.exports = factory(function (name) { return require(name); });
|
||||
else window.asn1 = factory(function (name) { return window[name.substring(2)]; });
|
||||
})(function (require) {
|
||||
"use strict";
|
||||
|
||||
var Int10 = require('./int10'),
|
||||
oids = require('./oids'),
|
||||
ellipsis = "\u2026",
|
||||
reTimeS = /^(\d\d)(0[1-9]|1[0-2])(0[1-9]|[12]\d|3[01])([01]\d|2[0-3])(?:([0-5]\d)(?:([0-5]\d)(?:[.,](\d{1,3}))?)?)?(Z|[-+](?:[0]\d|1[0-2])([0-5]\d)?)?$/,
|
||||
reTimeL = /^(\d\d\d\d)(0[1-9]|1[0-2])(0[1-9]|[12]\d|3[01])([01]\d|2[0-3])(?:([0-5]\d)(?:([0-5]\d)(?:[.,](\d{1,3}))?)?)?(Z|[-+](?:[0]\d|1[0-2])([0-5]\d)?)?$/;
|
||||
|
||||
function stringCut(str, len) {
|
||||
if (str.length > len)
|
||||
str = str.substring(0, len) + ellipsis;
|
||||
return str;
|
||||
}
|
||||
|
||||
function Stream(enc, pos) {
|
||||
if (enc instanceof Stream) {
|
||||
this.enc = enc.enc;
|
||||
this.pos = enc.pos;
|
||||
} else {
|
||||
// enc should be an array or a binary string
|
||||
this.enc = enc;
|
||||
this.pos = pos;
|
||||
}
|
||||
}
|
||||
Stream.prototype.get = function (pos) {
|
||||
if (pos === undefined)
|
||||
pos = this.pos++;
|
||||
if (pos >= this.enc.length)
|
||||
throw 'Requesting byte offset ' + pos + ' on a stream of length ' + this.enc.length;
|
||||
return (typeof this.enc == "string") ? this.enc.charCodeAt(pos) : this.enc[pos];
|
||||
};
|
||||
Stream.prototype.hexDigits = "0123456789ABCDEF";
|
||||
Stream.prototype.hexByte = function (b) {
|
||||
return this.hexDigits.charAt((b >> 4) & 0xF) + this.hexDigits.charAt(b & 0xF);
|
||||
};
|
||||
Stream.prototype.hexDump = function (start, end, raw) {
|
||||
var s = "";
|
||||
for (var i = start; i < end; ++i) {
|
||||
s += this.hexByte(this.get(i));
|
||||
if (raw !== true)
|
||||
switch (i & 0xF) {
|
||||
case 0x7: s += " "; break;
|
||||
case 0xF: s += "\n"; break;
|
||||
default: s += " ";
|
||||
}
|
||||
}
|
||||
return s;
|
||||
};
|
||||
var b64Safe = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_";
|
||||
Stream.prototype.b64Dump = function (start, end) {
|
||||
var extra = (end - start) % 3,
|
||||
s = '',
|
||||
i, c;
|
||||
for (i = start; i + 2 < end; i += 3) {
|
||||
c = this.get(i) << 16 | this.get(i + 1) << 8 | this.get(i + 2);
|
||||
s += b64Safe.charAt(c >> 18 & 0x3F);
|
||||
s += b64Safe.charAt(c >> 12 & 0x3F);
|
||||
s += b64Safe.charAt(c >> 6 & 0x3F);
|
||||
s += b64Safe.charAt(c & 0x3F);
|
||||
}
|
||||
if (extra > 0) {
|
||||
c = this.get(i) << 16;
|
||||
if (extra > 1) c |= this.get(i + 1) << 8;
|
||||
s += b64Safe.charAt(c >> 18 & 0x3F);
|
||||
s += b64Safe.charAt(c >> 12 & 0x3F);
|
||||
if (extra == 2) s += b64Safe.charAt(c >> 6 & 0x3F);
|
||||
}
|
||||
return s;
|
||||
};
|
||||
Stream.prototype.isASCII = function (start, end) {
|
||||
for (var i = start; i < end; ++i) {
|
||||
var c = this.get(i);
|
||||
if (c < 32 || c > 176)
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
};
|
||||
Stream.prototype.parseStringISO = function (start, end) {
|
||||
var s = "";
|
||||
for (var i = start; i < end; ++i)
|
||||
s += String.fromCharCode(this.get(i));
|
||||
return s;
|
||||
};
|
||||
Stream.prototype.parseStringUTF = function (start, end) {
|
||||
function ex(c) { // must be 10xxxxxx
|
||||
if ((c < 0x80) || (c >= 0xC0))
|
||||
throw new Error('Invalid UTF-8 continuation byte: ' + c);
|
||||
return (c & 0x3F);
|
||||
}
|
||||
function surrogate(cp) {
|
||||
if (cp < 0x10000)
|
||||
throw new Error('UTF-8 overlong encoding, codepoint encoded in 4 bytes: ' + cp);
|
||||
// we could use String.fromCodePoint(cp) but let's be nice to older browsers and use surrogate pairs
|
||||
cp -= 0x10000;
|
||||
return String.fromCharCode((cp >> 10) + 0xD800, (cp & 0x3FF) + 0xDC00);
|
||||
}
|
||||
var s = "";
|
||||
for (var i = start; i < end; ) {
|
||||
var c = this.get(i++);
|
||||
if (c < 0x80) // 0xxxxxxx (7 bit)
|
||||
s += String.fromCharCode(c);
|
||||
else if (c < 0xC0)
|
||||
throw new Error('Invalid UTF-8 starting byte: ' + c);
|
||||
else if (c < 0xE0) // 110xxxxx 10xxxxxx (11 bit)
|
||||
s += String.fromCharCode(((c & 0x1F) << 6) | ex(this.get(i++)));
|
||||
else if (c < 0xF0) // 1110xxxx 10xxxxxx 10xxxxxx (16 bit)
|
||||
s += String.fromCharCode(((c & 0x0F) << 12) | (ex(this.get(i++)) << 6) | ex(this.get(i++)));
|
||||
else if (c < 0xF8) // 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx (21 bit)
|
||||
s += surrogate(((c & 0x07) << 18) | (ex(this.get(i++)) << 12) | (ex(this.get(i++)) << 6) | ex(this.get(i++)));
|
||||
else
|
||||
throw new Error('Invalid UTF-8 starting byte (since 2003 it is restricted to 4 bytes): ' + c);
|
||||
}
|
||||
return s;
|
||||
};
|
||||
Stream.prototype.parseStringBMP = function (start, end) {
|
||||
var str = "", hi, lo;
|
||||
for (var i = start; i < end; ) {
|
||||
hi = this.get(i++);
|
||||
lo = this.get(i++);
|
||||
str += String.fromCharCode((hi << 8) | lo);
|
||||
}
|
||||
return str;
|
||||
};
|
||||
Stream.prototype.parseTime = function (start, end, shortYear) {
|
||||
var s = this.parseStringISO(start, end),
|
||||
m = (shortYear ? reTimeS : reTimeL).exec(s);
|
||||
if (!m)
|
||||
return "Unrecognized time: " + s;
|
||||
if (shortYear) {
|
||||
// to avoid querying the timer, use the fixed range [1970, 2069]
|
||||
// it will conform with ITU X.400 [-10, +40] sliding window until 2030
|
||||
m[1] = +m[1];
|
||||
m[1] += (m[1] < 70) ? 2000 : 1900;
|
||||
}
|
||||
s = m[1] + "-" + m[2] + "-" + m[3] + " " + m[4];
|
||||
if (m[5]) {
|
||||
s += ":" + m[5];
|
||||
if (m[6]) {
|
||||
s += ":" + m[6];
|
||||
if (m[7])
|
||||
s += "." + m[7];
|
||||
}
|
||||
}
|
||||
if (m[8]) {
|
||||
s += " UTC";
|
||||
if (m[8] != 'Z') {
|
||||
s += m[8];
|
||||
if (m[9])
|
||||
s += ":" + m[9];
|
||||
}
|
||||
}
|
||||
return s;
|
||||
};
|
||||
Stream.prototype.parseInteger = function (start, end) {
|
||||
var v = this.get(start),
|
||||
neg = (v > 127),
|
||||
pad = neg ? 255 : 0,
|
||||
len,
|
||||
s = '';
|
||||
// skip unuseful bits (not allowed in DER)
|
||||
while (v == pad && ++start < end)
|
||||
v = this.get(start);
|
||||
len = end - start;
|
||||
if (len === 0)
|
||||
return neg ? '-1' : '0';
|
||||
// show bit length of huge integers
|
||||
if (len > 4) {
|
||||
s = v;
|
||||
len <<= 3;
|
||||
while (((s ^ pad) & 0x80) == 0) {
|
||||
s <<= 1;
|
||||
--len;
|
||||
}
|
||||
s = "(" + len + " bit)\n";
|
||||
}
|
||||
// decode the integer
|
||||
if (neg) v = v - 256;
|
||||
var n = new Int10(v);
|
||||
for (var i = start + 1; i < end; ++i)
|
||||
n.mulAdd(256, this.get(i));
|
||||
return s + n.toString();
|
||||
};
|
||||
Stream.prototype.parseBitString = function (start, end, maxLength) {
|
||||
var unusedBits = this.get(start);
|
||||
if (unusedBits > 7)
|
||||
throw 'Invalid BitString with unusedBits=' + unusedBits;
|
||||
var lenBit = ((end - start - 1) << 3) - unusedBits,
|
||||
s = "";
|
||||
for (var i = start + 1; i < end; ++i) {
|
||||
var b = this.get(i),
|
||||
skip = (i == end - 1) ? unusedBits : 0;
|
||||
for (var j = 7; j >= skip; --j)
|
||||
s += (b >> j) & 1 ? "1" : "0";
|
||||
if (s.length > maxLength)
|
||||
s = stringCut(s, maxLength);
|
||||
}
|
||||
return { size: lenBit, str: s };
|
||||
};
|
||||
Stream.prototype.parseOctetString = function (start, end, maxLength) {
|
||||
var len = end - start,
|
||||
s;
|
||||
try {
|
||||
s = this.parseStringUTF(start, end);
|
||||
var v;
|
||||
for (i = 0; i < s.length; ++i) {
|
||||
v = s.charCodeAt(i);
|
||||
if (v < 32 && v != 9 && v != 10 && v != 13) // [\t\r\n] are (kinda) printable
|
||||
throw new Error('Unprintable character at index ' + i + ' (code ' + s.charCodeAt(i) + ")");
|
||||
}
|
||||
return { size: len, str: s };
|
||||
} catch (e) {
|
||||
// ignore
|
||||
}
|
||||
maxLength /= 2; // we work in bytes
|
||||
if (len > maxLength)
|
||||
end = start + maxLength;
|
||||
s = '';
|
||||
for (var i = start; i < end; ++i)
|
||||
s += this.hexByte(this.get(i));
|
||||
if (len > maxLength)
|
||||
s += ellipsis;
|
||||
return { size: len, str: s };
|
||||
};
|
||||
Stream.prototype.parseOID = function (start, end, maxLength) {
|
||||
var s = '',
|
||||
n = new Int10(),
|
||||
bits = 0;
|
||||
for (var i = start; i < end; ++i) {
|
||||
var v = this.get(i);
|
||||
n.mulAdd(128, v & 0x7F);
|
||||
bits += 7;
|
||||
if (!(v & 0x80)) { // finished
|
||||
if (s === '') {
|
||||
n = n.simplify();
|
||||
if (n instanceof Int10) {
|
||||
n.sub(80);
|
||||
s = "2." + n.toString();
|
||||
} else {
|
||||
var m = n < 80 ? n < 40 ? 0 : 1 : 2;
|
||||
s = m + "." + (n - m * 40);
|
||||
}
|
||||
} else
|
||||
s += "." + n.toString();
|
||||
if (s.length > maxLength)
|
||||
return stringCut(s, maxLength);
|
||||
n = new Int10();
|
||||
bits = 0;
|
||||
}
|
||||
}
|
||||
if (bits > 0)
|
||||
s += ".incomplete";
|
||||
if (typeof oids === 'object') {
|
||||
var oid = oids[s];
|
||||
if (oid) {
|
||||
if (oid.d) s += "\n" + oid.d;
|
||||
if (oid.c) s += "\n" + oid.c;
|
||||
if (oid.w) s += "\n(warning!)";
|
||||
}
|
||||
}
|
||||
return s;
|
||||
};
|
||||
|
||||
function ASN1(stream, header, length, tag, tagLen, sub) {
|
||||
if (!(tag instanceof ASN1Tag)) throw 'Invalid tag value.';
|
||||
this.stream = stream;
|
||||
this.header = header;
|
||||
this.length = length;
|
||||
this.tag = tag;
|
||||
this.tagLen = tagLen;
|
||||
this.sub = sub;
|
||||
}
|
||||
ASN1.prototype.typeName = function () {
|
||||
switch (this.tag.tagClass) {
|
||||
case 0: // universal
|
||||
switch (this.tag.tagNumber) {
|
||||
case 0x00: return "EOC";
|
||||
case 0x01: return "BOOLEAN";
|
||||
case 0x02: return "INTEGER";
|
||||
case 0x03: return "BIT_STRING";
|
||||
case 0x04: return "OCTET_STRING";
|
||||
case 0x05: return "NULL";
|
||||
case 0x06: return "OBJECT_IDENTIFIER";
|
||||
case 0x07: return "ObjectDescriptor";
|
||||
case 0x08: return "EXTERNAL";
|
||||
case 0x09: return "REAL";
|
||||
case 0x0A: return "ENUMERATED";
|
||||
case 0x0B: return "EMBEDDED_PDV";
|
||||
case 0x0C: return "UTF8String";
|
||||
case 0x10: return "SEQUENCE";
|
||||
case 0x11: return "SET";
|
||||
case 0x12: return "NumericString";
|
||||
case 0x13: return "PrintableString"; // ASCII subset
|
||||
case 0x14: return "TeletexString"; // aka T61String
|
||||
case 0x15: return "VideotexString";
|
||||
case 0x16: return "IA5String"; // ASCII
|
||||
case 0x17: return "UTCTime";
|
||||
case 0x18: return "GeneralizedTime";
|
||||
case 0x19: return "GraphicString";
|
||||
case 0x1A: return "VisibleString"; // ASCII subset
|
||||
case 0x1B: return "GeneralString";
|
||||
case 0x1C: return "UniversalString";
|
||||
case 0x1E: return "BMPString";
|
||||
}
|
||||
return "Universal_" + this.tag.tagNumber.toString();
|
||||
case 1: return "Application_" + this.tag.tagNumber.toString();
|
||||
case 2: return "[" + this.tag.tagNumber.toString() + "]"; // Context
|
||||
case 3: return "Private_" + this.tag.tagNumber.toString();
|
||||
}
|
||||
};
|
||||
function recurse(el, parser, maxLength) {
|
||||
var avoidRecurse = true;
|
||||
if (el.tag.tagConstructed && el.sub) {
|
||||
avoidRecurse = false;
|
||||
el.sub.forEach(function (e1) {
|
||||
if (e1.tag.tagClass != el.tag.tagClass || e1.tag.tagNumber != el.tag.tagNumber)
|
||||
avoidRecurse = true;
|
||||
});
|
||||
}
|
||||
if (avoidRecurse)
|
||||
return el.stream[parser](el.posContent(), el.posContent() + Math.abs(el.length), maxLength);
|
||||
var d = { size: 0, str: '' };
|
||||
el.sub.forEach(function (el) {
|
||||
var d1 = recurse(el, parser, maxLength - d.str.length);
|
||||
d.size += d1.size;
|
||||
d.str += d1.str;
|
||||
});
|
||||
return d;
|
||||
}
|
||||
/** A string preview of the content (intended for humans). */
|
||||
ASN1.prototype.content = function (maxLength) {
|
||||
if (this.tag === undefined)
|
||||
return null;
|
||||
if (maxLength === undefined)
|
||||
maxLength = Infinity;
|
||||
var content = this.posContent(),
|
||||
len = Math.abs(this.length);
|
||||
if (!this.tag.isUniversal()) {
|
||||
if (this.sub !== null)
|
||||
return "(" + this.sub.length + " elem)";
|
||||
var d1 = this.stream.parseOctetString(content, content + len, maxLength);
|
||||
return "(" + d1.size + " byte)\n" + d1.str;
|
||||
}
|
||||
switch (this.tag.tagNumber) {
|
||||
case 0x01: // BOOLEAN
|
||||
return (this.stream.get(content) === 0) ? "false" : "true";
|
||||
case 0x02: // INTEGER
|
||||
return this.stream.parseInteger(content, content + len);
|
||||
case 0x03: // BIT_STRING
|
||||
var d = recurse(this, 'parseBitString', maxLength);
|
||||
return "(" + d.size + " bit)\n" + d.str;
|
||||
case 0x04: // OCTET_STRING
|
||||
d = recurse(this, 'parseOctetString', maxLength);
|
||||
return "(" + d.size + " byte)\n" + d.str;
|
||||
//case 0x05: // NULL
|
||||
case 0x06: // OBJECT_IDENTIFIER
|
||||
return this.stream.parseOID(content, content + len, maxLength);
|
||||
//case 0x07: // ObjectDescriptor
|
||||
//case 0x08: // EXTERNAL
|
||||
//case 0x09: // REAL
|
||||
case 0x0A: // ENUMERATED
|
||||
return this.stream.parseInteger(content, content + len);
|
||||
//case 0x0B: // EMBEDDED_PDV
|
||||
case 0x10: // SEQUENCE
|
||||
case 0x11: // SET
|
||||
if (this.sub !== null)
|
||||
return "(" + this.sub.length + " elem)";
|
||||
else
|
||||
return "(no elem)";
|
||||
case 0x0C: // UTF8String
|
||||
return stringCut(this.stream.parseStringUTF(content, content + len), maxLength);
|
||||
case 0x12: // NumericString
|
||||
case 0x13: // PrintableString
|
||||
case 0x14: // TeletexString
|
||||
case 0x15: // VideotexString
|
||||
case 0x16: // IA5String
|
||||
case 0x1A: // VisibleString
|
||||
case 0x1B: // GeneralString
|
||||
//case 0x19: // GraphicString
|
||||
//case 0x1C: // UniversalString
|
||||
return stringCut(this.stream.parseStringISO(content, content + len), maxLength);
|
||||
case 0x1E: // BMPString
|
||||
return stringCut(this.stream.parseStringBMP(content, content + len), maxLength);
|
||||
case 0x17: // UTCTime
|
||||
case 0x18: // GeneralizedTime
|
||||
return this.stream.parseTime(content, content + len, (this.tag.tagNumber == 0x17));
|
||||
}
|
||||
return null;
|
||||
};
|
||||
ASN1.prototype.toString = function () {
|
||||
return this.typeName() + "@" + this.stream.pos + "[header:" + this.header + ",length:" + this.length + ",sub:" + ((this.sub === null) ? 'null' : this.sub.length) + "]";
|
||||
};
|
||||
ASN1.prototype.toPrettyString = function (indent) {
|
||||
if (indent === undefined) indent = '';
|
||||
var s = indent + this.typeName() + " @" + this.stream.pos;
|
||||
if (this.length >= 0)
|
||||
s += "+";
|
||||
s += this.length;
|
||||
if (this.tag.tagConstructed)
|
||||
s += " (constructed)";
|
||||
else if ((this.tag.isUniversal() && ((this.tag.tagNumber == 0x03) || (this.tag.tagNumber == 0x04))) && (this.sub !== null))
|
||||
s += " (encapsulates)";
|
||||
var content = this.content();
|
||||
if (content)
|
||||
s += ": " + content.replace(/\n/g, '|');
|
||||
s += "\n";
|
||||
if (this.sub !== null) {
|
||||
indent += ' ';
|
||||
for (var i = 0, max = this.sub.length; i < max; ++i)
|
||||
s += this.sub[i].toPrettyString(indent);
|
||||
}
|
||||
return s;
|
||||
};
|
||||
ASN1.prototype.posStart = function () {
|
||||
return this.stream.pos;
|
||||
};
|
||||
ASN1.prototype.posContent = function () {
|
||||
return this.stream.pos + this.header;
|
||||
};
|
||||
ASN1.prototype.posEnd = function () {
|
||||
return this.stream.pos + this.header + Math.abs(this.length);
|
||||
};
|
||||
/** Position of the length. */
|
||||
ASN1.prototype.posLen = function() {
|
||||
return this.stream.pos + this.tagLen;
|
||||
};
|
||||
ASN1.prototype.toHexString = function () {
|
||||
return this.stream.hexDump(this.posStart(), this.posEnd(), true);
|
||||
};
|
||||
ASN1.prototype.toB64String = function () {
|
||||
return this.stream.b64Dump(this.posStart(), this.posEnd());
|
||||
};
|
||||
ASN1.decodeLength = function (stream) {
|
||||
var buf = stream.get(),
|
||||
len = buf & 0x7F;
|
||||
if (len == buf) // first bit was 0, short form
|
||||
return len;
|
||||
if (len === 0) // long form with length 0 is a special case
|
||||
return null; // undefined length
|
||||
if (len > 6) // no reason to use Int10, as it would be a huge buffer anyways
|
||||
throw "Length over 48 bits not supported at position " + (stream.pos - 1);
|
||||
buf = 0;
|
||||
for (var i = 0; i < len; ++i)
|
||||
buf = (buf * 256) + stream.get();
|
||||
return buf;
|
||||
};
|
||||
function ASN1Tag(stream) {
|
||||
var buf = stream.get();
|
||||
this.tagClass = buf >> 6;
|
||||
this.tagConstructed = ((buf & 0x20) !== 0);
|
||||
this.tagNumber = buf & 0x1F;
|
||||
if (this.tagNumber == 0x1F) { // long tag
|
||||
var n = new Int10();
|
||||
do {
|
||||
buf = stream.get();
|
||||
n.mulAdd(128, buf & 0x7F);
|
||||
} while (buf & 0x80);
|
||||
this.tagNumber = n.simplify();
|
||||
}
|
||||
}
|
||||
ASN1Tag.prototype.isUniversal = function () {
|
||||
return this.tagClass === 0x00;
|
||||
};
|
||||
ASN1Tag.prototype.isEOC = function () {
|
||||
return this.tagClass === 0x00 && this.tagNumber === 0x00;
|
||||
};
|
||||
ASN1.decode = function (stream, offset) {
|
||||
if (!(stream instanceof Stream))
|
||||
stream = new Stream(stream, offset || 0);
|
||||
var streamStart = new Stream(stream),
|
||||
tag = new ASN1Tag(stream),
|
||||
tagLen = stream.pos - streamStart.pos,
|
||||
len = ASN1.decodeLength(stream),
|
||||
start = stream.pos,
|
||||
header = start - streamStart.pos,
|
||||
sub = null,
|
||||
getSub = function () {
|
||||
sub = [];
|
||||
if (len !== null) {
|
||||
// definite length
|
||||
var end = start + len;
|
||||
if (end > stream.enc.length)
|
||||
throw 'Container at offset ' + start + ' has a length of ' + len + ', which is past the end of the stream';
|
||||
while (stream.pos < end)
|
||||
sub[sub.length] = ASN1.decode(stream);
|
||||
if (stream.pos != end)
|
||||
throw 'Content size is not correct for container at offset ' + start;
|
||||
} else {
|
||||
// undefined length
|
||||
try {
|
||||
for (;;) {
|
||||
var s = ASN1.decode(stream);
|
||||
if (s.tag.isEOC())
|
||||
break;
|
||||
sub[sub.length] = s;
|
||||
}
|
||||
len = start - stream.pos; // undefined lengths are represented as negative values
|
||||
} catch (e) {
|
||||
throw 'Exception while decoding undefined length content at offset ' + start + ': ' + e;
|
||||
}
|
||||
}
|
||||
};
|
||||
if (tag.tagConstructed) {
|
||||
// must have valid content
|
||||
getSub();
|
||||
} else if (tag.isUniversal() && ((tag.tagNumber == 0x03) || (tag.tagNumber == 0x04))) {
|
||||
// sometimes BitString and OctetString are used to encapsulate ASN.1
|
||||
try {
|
||||
if (tag.tagNumber == 0x03)
|
||||
if (stream.get() != 0)
|
||||
throw "BIT STRINGs with unused bits cannot encapsulate.";
|
||||
getSub();
|
||||
for (var i = 0; i < sub.length; ++i)
|
||||
if (sub[i].tag.isEOC())
|
||||
throw 'EOC is not supposed to be actual content.';
|
||||
} catch (e) {
|
||||
// but silently ignore when they don't
|
||||
sub = null;
|
||||
//DEBUG console.log('Could not decode structure at ' + start + ':', e);
|
||||
}
|
||||
}
|
||||
if (sub === null) {
|
||||
if (len === null)
|
||||
throw "We can't skip over an invalid tag with undefined length at offset " + start;
|
||||
stream.pos = start + Math.abs(len);
|
||||
}
|
||||
return new ASN1(streamStart, header, len, tag, tagLen, sub);
|
||||
};
|
||||
|
||||
return ASN1;
|
||||
|
||||
});
|
||||
@@ -0,0 +1,105 @@
|
||||
// Base64 JavaScript decoder
|
||||
// Copyright (c) 2008-2020 Lapo Luchini <lapo@lapo.it>
|
||||
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
(typeof define != 'undefined' ? define : function (factory) { 'use strict';
|
||||
if (typeof module == 'object') module.exports = factory();
|
||||
else window.base64 = factory();
|
||||
})(function () {
|
||||
"use strict";
|
||||
|
||||
var Base64 = {},
|
||||
decoder, // populated on first usage
|
||||
haveU8 = (typeof Uint8Array == 'function');
|
||||
|
||||
Base64.decode = function (a) {
|
||||
var isString = (typeof a == 'string');
|
||||
var i;
|
||||
if (decoder === undefined) {
|
||||
var b64 = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/",
|
||||
ignore = "= \f\n\r\t\u00A0\u2028\u2029";
|
||||
decoder = [];
|
||||
for (i = 0; i < 64; ++i)
|
||||
decoder[b64.charCodeAt(i)] = i;
|
||||
for (i = 0; i < ignore.length; ++i)
|
||||
decoder[ignore.charCodeAt(i)] = -1;
|
||||
// RFC 3548 URL & file safe encoding
|
||||
decoder['-'.charCodeAt(0)] = decoder['+'.charCodeAt(0)];
|
||||
decoder['_'.charCodeAt(0)] = decoder['/'.charCodeAt(0)];
|
||||
}
|
||||
var out = haveU8 ? new Uint8Array(a.length * 3 >> 2) : [];
|
||||
var bits = 0, char_count = 0, len = 0;
|
||||
for (i = 0; i < a.length; ++i) {
|
||||
var c = isString ? a.charCodeAt(i) : a[i];
|
||||
if (c == 61) // '='.charCodeAt(0)
|
||||
break;
|
||||
c = decoder[c];
|
||||
if (c == -1)
|
||||
continue;
|
||||
if (c === undefined)
|
||||
throw 'Illegal character at offset ' + i;
|
||||
bits |= c;
|
||||
if (++char_count >= 4) {
|
||||
out[len++] = (bits >> 16);
|
||||
out[len++] = (bits >> 8) & 0xFF;
|
||||
out[len++] = bits & 0xFF;
|
||||
bits = 0;
|
||||
char_count = 0;
|
||||
} else {
|
||||
bits <<= 6;
|
||||
}
|
||||
}
|
||||
switch (char_count) {
|
||||
case 1:
|
||||
throw "Base64 encoding incomplete: at least 2 bits missing";
|
||||
case 2:
|
||||
out[len++] = (bits >> 10);
|
||||
break;
|
||||
case 3:
|
||||
out[len++] = (bits >> 16);
|
||||
out[len++] = (bits >> 8) & 0xFF;
|
||||
break;
|
||||
}
|
||||
if (haveU8 && out.length > len) // in case it was originally longer because of ignored characters
|
||||
out = out.subarray(0, len);
|
||||
return out;
|
||||
};
|
||||
|
||||
Base64.pretty = function (str) {
|
||||
// fix padding
|
||||
if (str.length % 4 > 0)
|
||||
str = (str + '===').slice(0, str.length + str.length % 4);
|
||||
// convert RFC 3548 to standard Base64
|
||||
str = str.replace(/-/g, '+').replace(/_/g, '/');
|
||||
// 80 column width
|
||||
return str.replace(/(.{80})/g, '$1\n');
|
||||
};
|
||||
|
||||
Base64.re = /-----BEGIN [^-]+-----([A-Za-z0-9+/=\s]+)-----END [^-]+-----|begin-base64[^\n]+\n([A-Za-z0-9+/=\s]+)====/;
|
||||
Base64.unarmor = function (a) {
|
||||
var m = Base64.re.exec(a);
|
||||
if (m) {
|
||||
if (m[1])
|
||||
a = m[1];
|
||||
else if (m[2])
|
||||
a = m[2];
|
||||
else
|
||||
throw "RegExp out of sync";
|
||||
}
|
||||
return Base64.decode(a);
|
||||
};
|
||||
|
||||
return Base64;
|
||||
|
||||
});
|
||||
@@ -0,0 +1,3 @@
|
||||
#!/bin/sh
|
||||
type gsha256sum >/dev/null && SHA256=gsha256sum || SHA256=sha256sum
|
||||
gpg --verify -o - sha256sums.asc | $SHA256 -c --quiet
|
||||
+220
@@ -0,0 +1,220 @@
|
||||
// ASN.1 JavaScript decoder
|
||||
// Copyright (c) 2008-2020 Lapo Luchini <lapo@lapo.it>
|
||||
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
(typeof define != 'undefined' ? define : function (factory) { 'use strict';
|
||||
if (typeof module == 'object') factory(function (name) { return require(name); });
|
||||
else factory(function (name) { return window[name.substring(2)]; });
|
||||
})(function (require) {
|
||||
"use strict";
|
||||
|
||||
var ASN1 = require('./asn1'),
|
||||
oids = require('./oids'),
|
||||
lineLength = 80,
|
||||
contentLength = 8 * lineLength,
|
||||
DOM = {
|
||||
ellipsis: "...",
|
||||
tag: function (tagName, className) {
|
||||
var t = document.createElement(tagName);
|
||||
t.className = className;
|
||||
return t;
|
||||
},
|
||||
text: function (str) {
|
||||
return document.createTextNode(str);
|
||||
},
|
||||
space: function () {
|
||||
var t = document.createElement('span');
|
||||
t.className = 'spaces';
|
||||
t.innerHTML = ' ';
|
||||
return t;
|
||||
},
|
||||
breakLines: function (str, length) {
|
||||
var lines = str.split(/\r?\n/),
|
||||
o = '';
|
||||
for (var i = 0; i < lines.length; ++i) {
|
||||
var line = lines[i];
|
||||
if (i > 0) o += "\n";
|
||||
while (line.length > length) {
|
||||
o += line.substring(0, length);
|
||||
o += "\n";
|
||||
line = line.substring(length);
|
||||
}
|
||||
o += line;
|
||||
}
|
||||
return o;
|
||||
}
|
||||
};
|
||||
|
||||
ASN1.prototype.toDOM = function (spaces) {
|
||||
spaces = spaces || '';
|
||||
var isOID = (typeof oids === 'object') && (this.tag.isUniversal() && (this.tag.tagNumber == 0x06));
|
||||
var node = DOM.tag("div", "node");
|
||||
node.asn1 = this;
|
||||
var head = DOM.tag("div", "head");
|
||||
head.innerHTML = "<span class='spaces'>" + spaces + "</span>" + this.typeName().replace(/_/g, " ");
|
||||
var content = this.content(contentLength);
|
||||
if (content !== null) {
|
||||
var preview = DOM.tag("span", "preview"),
|
||||
shortContent;
|
||||
if (isOID)
|
||||
content = content.split('\n', 1)[0];
|
||||
shortContent = (content.length > lineLength) ? content.substring(0, lineLength) + DOM.ellipsis : content;
|
||||
preview.appendChild(DOM.space());
|
||||
preview.appendChild(DOM.text(shortContent));
|
||||
if (isOID) {
|
||||
var oid = oids[content];
|
||||
if (oid) {
|
||||
if (oid.d) {
|
||||
preview.appendChild(DOM.space());
|
||||
var oidd = DOM.tag("span", "oid description");
|
||||
oidd.appendChild(DOM.text(oid.d));
|
||||
preview.appendChild(oidd);
|
||||
}
|
||||
if (oid.c) {
|
||||
preview.appendChild(DOM.space());
|
||||
var oidc = DOM.tag("span", "oid comment");
|
||||
oidc.appendChild(DOM.text("(" + oid.c + ")"));
|
||||
preview.appendChild(oidc);
|
||||
}
|
||||
}
|
||||
}
|
||||
head.appendChild(preview);
|
||||
content = DOM.breakLines(content, lineLength);
|
||||
content = content.replace(/</g, "<");
|
||||
content = content.replace(/\n/g, "<br>");
|
||||
}
|
||||
node.appendChild(head);
|
||||
this.node = node;
|
||||
this.head = head;
|
||||
var value = DOM.tag("div", "value");
|
||||
var s = "Offset: " + this.stream.pos + "<br>";
|
||||
s += "Length: " + this.header + "+";
|
||||
if (this.length >= 0)
|
||||
s += this.length;
|
||||
else
|
||||
s += (-this.length) + " (undefined)";
|
||||
if (this.tag.tagConstructed)
|
||||
s += "<br>(constructed)";
|
||||
else if ((this.tag.isUniversal() && ((this.tag.tagNumber == 0x03) || (this.tag.tagNumber == 0x04))) && (this.sub !== null))
|
||||
s += "<br>(encapsulates)";
|
||||
//TODO if (this.tag.isUniversal() && this.tag.tagNumber == 0x03) s += "Unused bits: "
|
||||
if (content !== null) {
|
||||
s += "<br>Value:<br><b>" + content + "</b>";
|
||||
if (isOID && oid) {
|
||||
if (oid.d) s += "<br>" + oid.d;
|
||||
if (oid.c) s += "<br>" + oid.c;
|
||||
if (oid.w) s += "<br>(warning!)";
|
||||
}
|
||||
}
|
||||
value.innerHTML = s;
|
||||
node.appendChild(value);
|
||||
var sub = DOM.tag("div", "sub");
|
||||
if (this.sub !== null) {
|
||||
spaces += '\xA0 ';
|
||||
for (var i = 0, max = this.sub.length; i < max; ++i)
|
||||
sub.appendChild(this.sub[i].toDOM(spaces));
|
||||
}
|
||||
node.appendChild(sub);
|
||||
head.onclick = function () {
|
||||
node.className = (node.className == "node collapsed") ? "node" : "node collapsed";
|
||||
};
|
||||
return node;
|
||||
};
|
||||
ASN1.prototype.fakeHover = function (current) {
|
||||
this.node.className += " hover";
|
||||
if (current)
|
||||
this.head.className += " hover";
|
||||
};
|
||||
ASN1.prototype.fakeOut = function (current) {
|
||||
var re = / ?hover/;
|
||||
this.node.className = this.node.className.replace(re, "");
|
||||
if (current)
|
||||
this.head.className = this.head.className.replace(re, "");
|
||||
};
|
||||
ASN1.prototype.toHexDOM_sub = function (node, className, stream, start, end) {
|
||||
if (start >= end)
|
||||
return;
|
||||
var sub = DOM.tag("span", className);
|
||||
sub.appendChild(DOM.text(
|
||||
stream.hexDump(start, end)));
|
||||
node.appendChild(sub);
|
||||
};
|
||||
ASN1.prototype.toHexDOM = function (root) {
|
||||
var node = DOM.tag("span", "hex");
|
||||
if (root === undefined) root = node;
|
||||
this.head.hexNode = node;
|
||||
this.head.onmouseover = function () { this.hexNode.className = "hexCurrent"; };
|
||||
this.head.onmouseout = function () { this.hexNode.className = "hex"; };
|
||||
node.asn1 = this;
|
||||
node.onmouseover = function () {
|
||||
var current = !root.selected;
|
||||
if (current) {
|
||||
root.selected = this.asn1;
|
||||
this.className = "hexCurrent";
|
||||
}
|
||||
this.asn1.fakeHover(current);
|
||||
};
|
||||
node.onmouseout = function () {
|
||||
var current = (root.selected == this.asn1);
|
||||
this.asn1.fakeOut(current);
|
||||
if (current) {
|
||||
root.selected = null;
|
||||
this.className = "hex";
|
||||
}
|
||||
};
|
||||
if (root == node) {
|
||||
var lineStart = this.posStart() & 0xF;
|
||||
if (lineStart != 0) {
|
||||
var skip = DOM.tag("span", "skip");
|
||||
var skipStr = '';
|
||||
for (var j = lineStart; j > 0; --j)
|
||||
skipStr += ' ';
|
||||
if (lineStart >= 8)
|
||||
skipStr += ' ';
|
||||
skip.innerText = skipStr;
|
||||
node.appendChild(skip);
|
||||
}
|
||||
}
|
||||
this.toHexDOM_sub(node, "tag", this.stream, this.posStart(), this.posLen());
|
||||
this.toHexDOM_sub(node, (this.length >= 0) ? "dlen" : "ulen", this.stream, this.posLen(), this.posContent());
|
||||
if (this.sub === null) {
|
||||
var start = this.posContent();
|
||||
var end = this.posEnd();
|
||||
if (end - start < 10 * 16)
|
||||
node.appendChild(DOM.text(
|
||||
this.stream.hexDump(start, end)));
|
||||
else {
|
||||
var end1 = start + 5 * 16 - (start & 0xF);
|
||||
var start2 = end - 16 - (end & 0xF);
|
||||
node.appendChild(DOM.text(
|
||||
this.stream.hexDump(start, end1)));
|
||||
var sub = DOM.tag("span", "skip");
|
||||
sub.appendChild(DOM.text("\u2026 skipping " + (start2 - end1) + " bytes \u2026\n"));
|
||||
node.appendChild(sub);
|
||||
node.appendChild(DOM.text(
|
||||
this.stream.hexDump(start2, end)));
|
||||
}
|
||||
} else if (this.sub.length > 0) {
|
||||
var first = this.sub[0];
|
||||
var last = this.sub[this.sub.length - 1];
|
||||
this.toHexDOM_sub(node, "intro", this.stream, this.posContent(), first.posStart());
|
||||
for (var i = 0, max = this.sub.length; i < max; ++i)
|
||||
node.appendChild(this.sub[i].toHexDOM(root));
|
||||
this.toHexDOM_sub(node, "outro", this.stream, last.posEnd(), this.posEnd());
|
||||
} else
|
||||
this.toHexDOM_sub(node, "outro", this.stream, this.posContent(), this.posEnd());
|
||||
return node;
|
||||
};
|
||||
|
||||
});
|
||||
@@ -0,0 +1,13 @@
|
||||
X.509 certificate based on Daniel J. Bernstein’s Curve25519 (as per RFC 8410).
|
||||
$ openssl req -x509 -newkey ed25519 -keyout test.key -out test.cer -days 3652 -subj '/C=IT/L=Milano/CN=Test ed25519'
|
||||
-----BEGIN CERTIFICATE-----
|
||||
MIIBfzCCATGgAwIBAgIUfI5kSdcO2S0+LkpdL3b2VUJG10YwBQYDK2VwMDUxCzAJ
|
||||
BgNVBAYTAklUMQ8wDQYDVQQHDAZNaWxhbm8xFTATBgNVBAMMDFRlc3QgZWQyNTUx
|
||||
OTAeFw0yMDA5MDIxMzI1MjZaFw0zMDA5MDIxMzI1MjZaMDUxCzAJBgNVBAYTAklU
|
||||
MQ8wDQYDVQQHDAZNaWxhbm8xFTATBgNVBAMMDFRlc3QgZWQyNTUxOTAqMAUGAytl
|
||||
cAMhADupL/3LF2beQKKS95PeMPgKI6gxIV3QB9hjJC7/aCGFo1MwUTAdBgNVHQ4E
|
||||
FgQUa6W9z536I1l4EmQXrh5y2JqASugwHwYDVR0jBBgwFoAUa6W9z536I1l4EmQX
|
||||
rh5y2JqASugwDwYDVR0TAQH/BAUwAwEB/zAFBgMrZXADQQBvc3e+KJZaMzbX5TT9
|
||||
kPP9QH8fAvkAV/IWDxZrBL9lhLaY0tDSv0zWbw624uidBKPgmVD5wm3ec60dNVeF
|
||||
ZYYG
|
||||
-----END CERTIFICATE-----
|
||||
@@ -0,0 +1,5 @@
|
||||
-----BEGIN ENCRYPTED PRIVATE KEY-----
|
||||
MIGKME4GCSqGSIb3DQEFDTBBMCkGCSqGSIb3DQEFDDAcBAgJNWVeJ7I5bAICCAAw
|
||||
DAYIKoZIhvcNAgkFADAUBggqhkiG9w0DBwQIgQdqdEdiw2sEOKkWbTSCypOwJ6K1
|
||||
TMVh+O2YVE8bIKb7CdLVtNbwDW2UuMVlx5DwK5HdCcVYy3OWfW+SWjBTPU0f
|
||||
-----END ENCRYPTED PRIVATE KEY-----
|
||||
@@ -0,0 +1,29 @@
|
||||
This is a real-world X.509 certificate, specifically a root CA.
|
||||
https://letsencrypt.org/certificates/
|
||||
-----BEGIN CERTIFICATE-----
|
||||
MIIEkjCCA3qgAwIBAgIQCgFBQgAAAVOFc2oLheynCDANBgkqhkiG9w0BAQsFADA/
|
||||
MSQwIgYDVQQKExtEaWdpdGFsIFNpZ25hdHVyZSBUcnVzdCBDby4xFzAVBgNVBAMT
|
||||
DkRTVCBSb290IENBIFgzMB4XDTE2MDMxNzE2NDA0NloXDTIxMDMxNzE2NDA0Nlow
|
||||
SjELMAkGA1UEBhMCVVMxFjAUBgNVBAoTDUxldCdzIEVuY3J5cHQxIzAhBgNVBAMT
|
||||
GkxldCdzIEVuY3J5cHQgQXV0aG9yaXR5IFgzMIIBIjANBgkqhkiG9w0BAQEFAAOC
|
||||
AQ8AMIIBCgKCAQEAnNMM8FrlLke3cl03g7NoYzDq1zUmGSXhvb418XCSL7e4S0EF
|
||||
q6meNQhY7LEqxGiHC6PjdeTm86dicbp5gWAf15Gan/PQeGdxyGkOlZHP/uaZ6WA8
|
||||
SMx+yk13EiSdRxta67nsHjcAHJyse6cF6s5K671B5TaYucv9bTyWaN8jKkKQDIZ0
|
||||
Z8h/pZq4UmEUEz9l6YKHy9v6Dlb2honzhT+Xhq+w3Brvaw2VFn3EK6BlspkENnWA
|
||||
a6xK8xuQSXgvopZPKiAlKQTGdMDQMc2PMTiVFrqoM7hD8bEfwzB/onkxEz0tNvjj
|
||||
/PIzark5McWvxI0NHWQWM6r6hCm21AvA2H3DkwIDAQABo4IBfTCCAXkwEgYDVR0T
|
||||
AQH/BAgwBgEB/wIBADAOBgNVHQ8BAf8EBAMCAYYwfwYIKwYBBQUHAQEEczBxMDIG
|
||||
CCsGAQUFBzABhiZodHRwOi8vaXNyZy50cnVzdGlkLm9jc3AuaWRlbnRydXN0LmNv
|
||||
bTA7BggrBgEFBQcwAoYvaHR0cDovL2FwcHMuaWRlbnRydXN0LmNvbS9yb290cy9k
|
||||
c3Ryb290Y2F4My5wN2MwHwYDVR0jBBgwFoAUxKexpHsscfrb4UuQdf/EFWCFiRAw
|
||||
VAYDVR0gBE0wSzAIBgZngQwBAgEwPwYLKwYBBAGC3xMBAQEwMDAuBggrBgEFBQcC
|
||||
ARYiaHR0cDovL2Nwcy5yb290LXgxLmxldHNlbmNyeXB0Lm9yZzA8BgNVHR8ENTAz
|
||||
MDGgL6AthitodHRwOi8vY3JsLmlkZW50cnVzdC5jb20vRFNUUk9PVENBWDNDUkwu
|
||||
Y3JsMB0GA1UdDgQWBBSoSmpjBH3duubRObemRWXv86jsoTANBgkqhkiG9w0BAQsF
|
||||
AAOCAQEA3TPXEfNjWDjdGBX7CVW+dla5cEilaUcne8IkCJLxWh9KEik3JHRRHGJo
|
||||
uM2VcGfl96S8TihRzZvoroed6ti6WqEBmtzw3Wodatg+VyOeph4EYpr/1wXKtx8/
|
||||
wApIvJSwtmVi4MFU5aMqrSDE6ea73Mj2tcMyo5jMd6jmeWUHK8so/joWUoHOUgwu
|
||||
X4Po1QYz+3dszkDqMp4fklxBwXRsW10KXzPMTZ+sOPAveyxindmjkW8lGy+QsRlG
|
||||
PfZ+G6Z6h7mjem0Y+iWlkYcV4PIWL1iwBi8saCbGS5jN2p8M+X+Q7UNKEkROb3N6
|
||||
KOqkqm57TH2H3eDJAkSnh6/DNFu0Qg==
|
||||
-----END CERTIFICATE-----
|
||||
@@ -0,0 +1,233 @@
|
||||
This is a PKCS#7/CMS attached digital signature.
|
||||
It is signed using ecdsaWithSHA256 over NIST curve P-256.
|
||||
It contains 10034 bytes of data in a constructed BER OCTET STRING, in 1000 byte chunks.
|
||||
-----BEGIN PKCS7-----
|
||||
MIAGCSqGSIb3DQEHAqCAMIACAQExDzANBglghkgBZQMEAgEFADCABgkqhkiG9w0B
|
||||
BwGggCSABIID6EluaXppbyBjb250ZW51dG8uCkFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUEEggPoQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQQSC
|
||||
A+hBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBBIID6EFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUEEggPoQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQQSCA+hBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBBIID6EFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUEEggPoQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQQSCA+hBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBBIID6EFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUEEIkFBQUFBQUFBQUFBQUFBQUFBQQpGaW5lIGNvbnRlbnV0
|
||||
by4AAAAAAACggDCCAW4wggEUoAMCAQICEHOxx/3deIyIkyCp0XuJoeAwCgYIKoZI
|
||||
zj0EAwIwDzENMAsGA1UEAwwEVGVzdDAeFw0xODA3MTYxNTE3MDBaFw0xOTA3MTYx
|
||||
NTE3MDBaMA8xDTALBgNVBAMMBFRlc3QwWTATBgcqhkjOPQIBBggqhkjOPQMBBwNC
|
||||
AATrbIaVzrUdDj6payN4bRMzfGAeUx2vbtdADsmVqB5UpZcE9+lk6mFONMMV8Mfd
|
||||
HMIrtU+kIeN3TKwYbvkKqFKFo1IwUDAOBgNVHQ8BAf8EBAMCBPAwHQYDVR0OBBYE
|
||||
FGYNLdBLRe0zyKL5cUmFcsIIV7W+MB8GA1UdIwQYMBaAFGYNLdBLRe0zyKL5cUmF
|
||||
csIIV7W+MAoGCCqGSM49BAMCA0gAMEUCIQCtFrZzgrRCt4a+2k1d6koKNkBVMHNP
|
||||
QUvcH+W3VyGdJwIgI9eyft3ADE5ZUOYb1kCY76qlMy2dexTDe1ECpHf66X4AADGC
|
||||
AYowggGGAgEBMCMwDzENMAsGA1UEAwwEVGVzdAIQc7HH/d14jIiTIKnRe4mh4DAN
|
||||
BglghkgBZQMEAgEFAKCB9zAYBgkqhkiG9w0BCQMxCwYJKoZIhvcNAQcBMBwGCSqG
|
||||
SIb3DQEJBTEPFw0xODA3MTYxNTE3MDFaMCoGCSqGSIb3DQEJNDEdMBswDQYJYIZI
|
||||
AWUDBAIBBQChCgYIKoZIzj0EAwIwLwYJKoZIhvcNAQkEMSIEIHJMUbvnbaBa+yDL
|
||||
6OsDfNrhr9cTEl0twT1VLan0QtJNMGAGCyqGSIb3DQEJEAIvMVEwTzBNMEsEIF5A
|
||||
LYEW0KWtjD68a+15KzrU4fL/PAv0FDQzhfnLy7yzMCcwE6QRMA8xDTALBgNVBAMM
|
||||
BFRlc3QCEHOxx/3deIyIkyCp0XuJoeAwCgYIKoZIzj0EAwIERzBFAiBU+itM+1PZ
|
||||
77m5G8pCq4R7zQKe7OK/1vVjoTpf1mhg1wIhANyu8NdrnbnEID1copBIRB8tOm6H
|
||||
5tIcUY4bEZXEeK9cAAAAAAAA
|
||||
-----END PKCS7-----
|
||||
@@ -0,0 +1,232 @@
|
||||
This is a PKCS#7/CMS attached digital signature.
|
||||
It is signed using ecdsaWithSHA256 over NIST curve P-256.
|
||||
It contains 10034 bytes of data in a single DER OCTET STRING.
|
||||
-----BEGIN PKCS7-----
|
||||
MIIqdAYJKoZIhvcNAQcCoIIqZTCCKmECAQExDzANBglghkgBZQMEAgEFADCCJ0UG
|
||||
CSqGSIb3DQEHAaCCJzYEgicySW5pemlvIGNvbnRlbnV0by4KQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFBQUFB
|
||||
QUFBQQpGaW5lIGNvbnRlbnV0by6gggFyMIIBbjCCARSgAwIBAgIQYFzS1SZ1s5Kl
|
||||
qpsCsmpVZjAKBggqhkjOPQQDAjAPMQ0wCwYDVQQDDARUZXN0MB4XDTE4MDcxNjE0
|
||||
NTYzNVoXDTE5MDcxNjE0NTYzNVowDzENMAsGA1UEAwwEVGVzdDBZMBMGByqGSM49
|
||||
AgEGCCqGSM49AwEHA0IABCRMtswcaSH/Sdi+Jj4LfNBaKGVahGyCXsrm7OaaaiHE
|
||||
5PIgJMDp9OR0nJihrfJfkN5u+UgrZxiDpw60t6ufBkOjUjBQMA4GA1UdDwEB/wQE
|
||||
AwIE8DAdBgNVHQ4EFgQUw8CE33sEDbA4r1GM45f27CDWJuYwHwYDVR0jBBgwFoAU
|
||||
w8CE33sEDbA4r1GM45f27CDWJuYwCgYIKoZIzj0EAwIDSAAwRQIhAN5gHlc9r7Wb
|
||||
xVHVjj57ntoGEt0BEoBaIhe3NHWbiEQXAiBnw/3mB4DUHB16O5ApHz05xNwvIG3M
|
||||
ui+YLAa2fAmyMjGCAYowggGGAgEBMCMwDzENMAsGA1UEAwwEVGVzdAIQYFzS1SZ1
|
||||
s5KlqpsCsmpVZjANBglghkgBZQMEAgEFAKCB9zAYBgkqhkiG9w0BCQMxCwYJKoZI
|
||||
hvcNAQcBMBwGCSqGSIb3DQEJBTEPFw0xODA3MTYxNDU2MzVaMCoGCSqGSIb3DQEJ
|
||||
NDEdMBswDQYJYIZIAWUDBAIBBQChCgYIKoZIzj0EAwIwLwYJKoZIhvcNAQkEMSIE
|
||||
IHJMUbvnbaBa+yDL6OsDfNrhr9cTEl0twT1VLan0QtJNMGAGCyqGSIb3DQEJEAIv
|
||||
MVEwTzBNMEsEILq8CENMWCZzAeAGhh0n7KElZw55J5ckjnalcXpb+ZPCMCcwE6QR
|
||||
MA8xDTALBgNVBAMMBFRlc3QCEGBc0tUmdbOSpaqbArJqVWYwCgYIKoZIzj0EAwIE
|
||||
RzBFAiEA8QQwLqu0KOzI5xzi449svthIqOmitdXaGZM+SFyDzHECIAy7QKC3ubLg
|
||||
SJIGIvsob9FGlfJM9lC9qkC4hfhMNLu5
|
||||
-----END PKCS7-----
|
||||
@@ -0,0 +1,22 @@
|
||||
This is a PKCS#7/CMS detached digital signature.
|
||||
It is an old example generated in 2008 and as such uses obsolete cryptography: RSA1024 with SHA1.
|
||||
-----BEGIN PKCS7-----
|
||||
MIIDUAYJKoZIhvcNAQcCoIIDQTCCAz0CAQExCzAJBgUrDgMCGgUAMAsGCSqGSIb3
|
||||
DQEHAaCCAfMwggHvMIIBWKADAgECAhAvoXazbunwSfREtACZZhlFMA0GCSqGSIb3
|
||||
DQEBBQUAMAwxCjAIBgNVBAMMAWEwHhcNMDgxMDE1MTUwMzQxWhcNMDkxMDE1MTUw
|
||||
MzQxWjAMMQowCAYDVQQDDAFhMIGfMA0GCSqGSIb3DQEBAQUAA4GNADCBiQKBgQCJ
|
||||
Uwlwhu5hR8X01f+vG0mKPRHsVRjpZNxSEmsmFPdDiD9kylE3ertTDf0gRkpIvWfN
|
||||
J+eymuxoXF0Qgl5gXAVuSrjupGD6J+VapixJiwLXJHokmDihLs3zfGARz08O3qnO
|
||||
5ofBy0pRxq5isu/bAAcjoByZ1sI/g0iAuotC1UFObwIDAQABo1IwUDAOBgNVHQ8B
|
||||
Af8EBAMCBPAwHQYDVR0OBBYEFEIGXQB4h+04Z3y/n7Nv94+CqPitMB8GA1UdIwQY
|
||||
MBaAFEIGXQB4h+04Z3y/n7Nv94+CqPitMA0GCSqGSIb3DQEBBQUAA4GBAE0G7tAi
|
||||
aacJxvP3fhEj+yP9VDxL0omrRRAEaMXwWaBf/Ggk1T/u+8/CDAdjuGNCiF6ctooK
|
||||
c8u8KpnZJsGqnpGQ4n6L2KjTtRUDh+hija0eJRBFdirPQe2HAebQGFnmOk6Mn7Ki
|
||||
QfBIsOzXim/bFqaBSbf06bLTQNwFouSO+jwOMYIBJTCCASECAQEwIDAMMQowCAYD
|
||||
VQQDDAFhAhAvoXazbunwSfREtACZZhlFMAkGBSsOAwIaBQCgXTAYBgkqhkiG9w0B
|
||||
CQMxCwYJKoZIhvcNAQcBMBwGCSqGSIb3DQEJBTEPFw0wODEwMTUxNTAzNDNaMCMG
|
||||
CSqGSIb3DQEJBDEWBBQAAAAAAAAAAAAAAAAAAAAAAAAAADANBgkqhkiG9w0BAQEF
|
||||
AASBgHQe0ocjBn+ZVXWbb8CpZ2CxzFKiVrgZxZO2kMBwJoNyZx+jnICHdhfsX4Or
|
||||
cF5vIYVAZIRz5RxqFmuZELTfZ/K89zaK873DP9V7/ftBGpezWEp9h29AtAzI9lzS
|
||||
GB9gugiyB5JstXoM1L87KJmT05MeZxg1pvvFhwo1m/QOpcqz
|
||||
-----END PKCS7-----
|
||||
@@ -0,0 +1,74 @@
|
||||
// Hex JavaScript decoder
|
||||
// Copyright (c) 2008-2020 Lapo Luchini <lapo@lapo.it>
|
||||
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
(typeof define != 'undefined' ? define : function (factory) { 'use strict';
|
||||
if (typeof module == 'object') module.exports = factory();
|
||||
else window.hex = factory();
|
||||
})(function () {
|
||||
"use strict";
|
||||
|
||||
var Hex = {},
|
||||
decoder, // populated on first usage
|
||||
haveU8 = (typeof Uint8Array == 'function');
|
||||
|
||||
/**
|
||||
* Decodes an hexadecimal value.
|
||||
* @param {string|Array|Uint8Array} a - a string representing hexadecimal data, or an array representation of its charcodes
|
||||
*/
|
||||
Hex.decode = function(a) {
|
||||
var isString = (typeof a == 'string');
|
||||
var i;
|
||||
if (decoder === undefined) {
|
||||
var hex = "0123456789ABCDEF",
|
||||
ignore = " \f\n\r\t\u00A0\u2028\u2029";
|
||||
decoder = [];
|
||||
for (i = 0; i < 16; ++i)
|
||||
decoder[hex.charCodeAt(i)] = i;
|
||||
hex = hex.toLowerCase();
|
||||
for (i = 10; i < 16; ++i)
|
||||
decoder[hex.charCodeAt(i)] = i;
|
||||
for (i = 0; i < ignore.length; ++i)
|
||||
decoder[ignore.charCodeAt(i)] = -1;
|
||||
}
|
||||
var out = haveU8 ? new Uint8Array(a.length >> 1) : [],
|
||||
bits = 0,
|
||||
char_count = 0,
|
||||
len = 0;
|
||||
for (i = 0; i < a.length; ++i) {
|
||||
var c = isString ? a.charCodeAt(i) : a[i];
|
||||
c = decoder[c];
|
||||
if (c == -1)
|
||||
continue;
|
||||
if (c === undefined)
|
||||
throw 'Illegal character at offset ' + i;
|
||||
bits |= c;
|
||||
if (++char_count >= 2) {
|
||||
out[len++] = bits;
|
||||
bits = 0;
|
||||
char_count = 0;
|
||||
} else {
|
||||
bits <<= 4;
|
||||
}
|
||||
}
|
||||
if (char_count)
|
||||
throw "Hex encoding incomplete: 4 bits missing";
|
||||
if (haveU8 && out.length > len) // in case it was originally longer because of ignored characters
|
||||
out = out.subarray(0, len);
|
||||
return out;
|
||||
};
|
||||
|
||||
return Hex;
|
||||
|
||||
});
|
||||
@@ -0,0 +1,102 @@
|
||||
html, body {
|
||||
background-color: #C0C0C0;
|
||||
font-family: Arial, Helvetica, sans-serif;
|
||||
text-align: justify;
|
||||
}
|
||||
.tt {
|
||||
font-family: monospace;
|
||||
}
|
||||
.license .ref {
|
||||
position: relative;
|
||||
}
|
||||
.license .hidden {
|
||||
visibility: hidden;
|
||||
position: absolute;
|
||||
bottom: 0em;
|
||||
/*white-space: pre;*/
|
||||
background-color: #D0D0D0;
|
||||
border: solid 1px white;
|
||||
padding: 2px;
|
||||
margin-left: 15%;
|
||||
margin-right: 15%;
|
||||
}
|
||||
.license:hover .hidden {
|
||||
/*display: block;*/
|
||||
visibility: visible;
|
||||
}
|
||||
.node {
|
||||
position: relative;
|
||||
}
|
||||
.sub {
|
||||
padding-left: 1.5em;
|
||||
border-left: solid 1px #E0E0E0;
|
||||
}
|
||||
.head {
|
||||
height: 1em;
|
||||
white-space: nowrap;
|
||||
}
|
||||
.node:hover > .head, .node.hover > .head {
|
||||
color: darkblue;
|
||||
font-weight: bold;
|
||||
}
|
||||
.node:hover > .head:hover, .node.hover > .head.hover {
|
||||
color: blue;
|
||||
}
|
||||
.node.collapsed {
|
||||
font-style: italic;
|
||||
}
|
||||
.node.collapsed > .sub {
|
||||
display: none;
|
||||
}
|
||||
.node.collapsed.hover > .sub {
|
||||
display: block;
|
||||
}
|
||||
.value {
|
||||
display: none;
|
||||
position: absolute;
|
||||
z-index: 2;
|
||||
top: 1.2em;
|
||||
left: 0;
|
||||
background-color: #D0D0D0;
|
||||
border: solid 1px white;
|
||||
padding: 2px;
|
||||
}
|
||||
.head:hover + .value, .head.hover + .value {
|
||||
display: block;
|
||||
}
|
||||
.preview {
|
||||
margin-left: 1em;
|
||||
color: #505050;
|
||||
font-weight: normal;
|
||||
}
|
||||
.preview > .oid {
|
||||
margin-left: 1em;
|
||||
color: #808080;
|
||||
font-weight: normal;
|
||||
}
|
||||
.spaces {
|
||||
font-size: 0px;
|
||||
}
|
||||
#tree {
|
||||
font-family: monospace;
|
||||
}
|
||||
#tree > p {
|
||||
font-family: Arial, Helvetica, sans-serif;
|
||||
}
|
||||
#dump {
|
||||
z-index: 1;
|
||||
background-color: #C0C0C0;
|
||||
border: solid 1px #E0E0E0;
|
||||
font-family: monospace;
|
||||
white-space: pre;
|
||||
padding: 2px;
|
||||
}
|
||||
#dump .tag { color: blue; }
|
||||
#dump .dlen { color: darkcyan; }
|
||||
#dump .ulen { color: darkgreen; }
|
||||
#dump .intro { color: blue; }
|
||||
#dump .outro { color: darkgreen; }
|
||||
#dump .skip { color: #666666; background-color: #C0C0C0; }
|
||||
#dump .hexCurrent { background-color: #808080; }
|
||||
#dump .hexCurrent .hex { background-color: #A0A0A0; }
|
||||
#file { display: none; }
|
||||
@@ -0,0 +1,43 @@
|
||||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="US-ASCII">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
|
||||
<title>ASN.1 JavaScript decoder</title>
|
||||
<link rel="stylesheet" href="index.css" type="text/css">
|
||||
</head>
|
||||
<body style="padding: 3rem">
|
||||
<h1>ASN.1 JavaScript decoder</h1>
|
||||
<div style="position: relative; padding-bottom: 1em;">
|
||||
<div id="dump" style="position: absolute; right: 0px;"></div>
|
||||
<div id="tree"></div>
|
||||
</div>
|
||||
<form>
|
||||
<textarea id="area" style="width: 100%;" rows="8"></textarea>
|
||||
<br>
|
||||
<label title="can be slow with big files"><input type="checkbox" id="wantHex" checked="checked"> with hex dump</label>
|
||||
<input id="butDecode" type="button" value="decode">
|
||||
<input id="butClear" type="button" value="clear">
|
||||
<input type="file" id="file">
|
||||
<div>
|
||||
Examples:
|
||||
<select id="examples">
|
||||
<option value="sig-p256-der.p7m">PKCS#7/CMS attached signature (DER)</option>
|
||||
<option value="sig-p256-ber.p7m">PKCS#7/CMS attached signature (BER)</option>
|
||||
<option value="sig-rsa1024-sha1.p7s">PKCS#7/CMS detached signature (old)</option>
|
||||
<option value="letsencrypt-x3.cer">X.509 certificate: Let's Encrypt X3</option>
|
||||
<option value="ed25519.cer">X.509 certificate: ed25519 (RFC 8410)</option>
|
||||
</select>
|
||||
<input id="butExample" type="button" value="load example">
|
||||
</div>
|
||||
</form>
|
||||
|
||||
<script type="text/javascript" src="hex.js"></script>
|
||||
<script type="text/javascript" src="base64.js"></script>
|
||||
<script type="text/javascript" src="oids.js"></script>
|
||||
<script type="text/javascript" src="int10.js"></script>
|
||||
<script type="text/javascript" src="asn1.js"></script>
|
||||
<script type="text/javascript" src="dom.js"></script>
|
||||
<script type="text/javascript" src="index.js"></script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,164 @@
|
||||
(typeof define != 'undefined' ? define : function (factory) { 'use strict';
|
||||
if (typeof module == 'object') factory(function (name) { return require(name); });
|
||||
else factory(function (name) { return window[name.substring(2)]; });
|
||||
})(function (require) {
|
||||
"use strict";
|
||||
|
||||
var ASN1 = require('./asn1'),
|
||||
Base64 = require('./base64'),
|
||||
Hex = require('./hex'),
|
||||
maxLength = 10240,
|
||||
reHex = /^\s*(?:[0-9A-Fa-f][0-9A-Fa-f]\s*)+$/,
|
||||
tree = id('tree'),
|
||||
dump = id('dump'),
|
||||
wantHex = id('wantHex'),
|
||||
area = id('area'),
|
||||
file = id('file'),
|
||||
examples = id('examples'),
|
||||
hash = null;
|
||||
|
||||
require('./dom'); // side effect: augment ASN1
|
||||
if (!window.console || !window.console.log) // IE8 with closed developer tools
|
||||
window.console = { log: function () {} };
|
||||
function id(elem) {
|
||||
return document.getElementById(elem);
|
||||
}
|
||||
function text(el, string) {
|
||||
if ('textContent' in el)
|
||||
el.textContent = string;
|
||||
else
|
||||
el.innerText = string;
|
||||
}
|
||||
function decode(der, offset) {
|
||||
offset = offset || 0;
|
||||
tree.innerHTML = '';
|
||||
dump.innerHTML = '';
|
||||
try {
|
||||
var asn1 = ASN1.decode(der, offset);
|
||||
tree.appendChild(asn1.toDOM());
|
||||
if (wantHex.checked)
|
||||
dump.appendChild(asn1.toHexDOM());
|
||||
var b64 = (der.length < maxLength) ? asn1.toB64String() : '';
|
||||
if (area.value === '')
|
||||
area.value = Base64.pretty(b64);
|
||||
try {
|
||||
window.location.hash = hash = '#' + b64;
|
||||
} catch (e) { // fails with "Access Denied" on IE with URLs longer than ~2048 chars
|
||||
window.location.hash = hash = '#';
|
||||
}
|
||||
var endOffset = asn1.posEnd();
|
||||
if (endOffset < der.length) {
|
||||
var p = document.createElement('p');
|
||||
p.innerText = 'Input contains ' + (der.length - endOffset) + ' more bytes to decode.';
|
||||
var button = document.createElement('button');
|
||||
button.innerText = 'try to decode';
|
||||
button.onclick = function () {
|
||||
decode(der, endOffset);
|
||||
};
|
||||
p.appendChild(button);
|
||||
tree.insertBefore(p, tree.firstChild);
|
||||
}
|
||||
} catch (e) {
|
||||
text(tree, e);
|
||||
}
|
||||
}
|
||||
function decodeText(val) {
|
||||
try {
|
||||
var der = reHex.test(val) ? Hex.decode(val) : Base64.unarmor(val);
|
||||
decode(der);
|
||||
} catch (e) {
|
||||
text(tree, e);
|
||||
dump.innerHTML = '';
|
||||
}
|
||||
}
|
||||
function decodeBinaryString(str) {
|
||||
var der;
|
||||
try {
|
||||
if (reHex.test(str))
|
||||
der = Hex.decode(str);
|
||||
else if (Base64.re.test(str))
|
||||
der = Base64.unarmor(str);
|
||||
else
|
||||
der = str;
|
||||
decode(der);
|
||||
} catch (e) {
|
||||
text(tree, 'Cannot decode file.');
|
||||
dump.innerHTML = '';
|
||||
}
|
||||
}
|
||||
// set up buttons
|
||||
id('butDecode').onclick = function () { decodeText(area.value); };
|
||||
id('butClear').onclick = function () {
|
||||
area.value = '';
|
||||
file.value = '';
|
||||
tree.innerHTML = '';
|
||||
dump.innerHTML = '';
|
||||
hash = window.location.hash = '';
|
||||
};
|
||||
id('butExample').onclick = function () {
|
||||
console.log('Loading example:', examples.value);
|
||||
var request = new XMLHttpRequest();
|
||||
request.open('GET', 'examples/' + examples.value, true);
|
||||
request.onreadystatechange = function() {
|
||||
if (this.readyState !== 4)
|
||||
return;
|
||||
if (this.status >= 200 && this.status < 400) {
|
||||
area.value = this.responseText;
|
||||
decodeText(this.responseText);
|
||||
} else {
|
||||
console.log('Error loading example.');
|
||||
}
|
||||
};
|
||||
request.send();
|
||||
};
|
||||
// this is only used if window.FileReader
|
||||
function read(f) {
|
||||
area.value = ''; // clear text area, will get b64 content
|
||||
var r = new FileReader();
|
||||
r.onloadend = function () {
|
||||
if (r.error)
|
||||
alert("Your browser couldn't read the specified file (error code " + r.error.code + ").");
|
||||
else
|
||||
decodeBinaryString(r.result);
|
||||
};
|
||||
r.readAsBinaryString(f);
|
||||
}
|
||||
function load() {
|
||||
if (file.files.length === 0)
|
||||
alert("Select a file to load first.");
|
||||
else
|
||||
read(file.files[0]);
|
||||
}
|
||||
function loadFromHash() {
|
||||
if (window.location.hash && window.location.hash != hash) {
|
||||
hash = window.location.hash;
|
||||
// Firefox is not consistent with other browsers and returns an
|
||||
// already-decoded hash string so we risk double-decoding here,
|
||||
// but since % is not allowed in base64 nor hexadecimal, it's ok
|
||||
var val = decodeURIComponent(hash.substr(1));
|
||||
if (val.length)
|
||||
decodeText(val);
|
||||
}
|
||||
}
|
||||
function stop(e) {
|
||||
e.stopPropagation();
|
||||
e.preventDefault();
|
||||
}
|
||||
function dragAccept(e) {
|
||||
stop(e);
|
||||
if (e.dataTransfer.files.length > 0)
|
||||
read(e.dataTransfer.files[0]);
|
||||
}
|
||||
// main
|
||||
if ('onhashchange' in window)
|
||||
window.onhashchange = loadFromHash;
|
||||
loadFromHash();
|
||||
document.ondragover = stop;
|
||||
document.ondragleave = stop;
|
||||
if ('FileReader' in window && 'readAsBinaryString' in (new FileReader())) {
|
||||
file.style.display = 'block';
|
||||
file.onchange = load;
|
||||
document.ondrop = dragAccept;
|
||||
}
|
||||
|
||||
});
|
||||
@@ -0,0 +1,113 @@
|
||||
// Big integer base-10 printing library
|
||||
// Copyright (c) 2008-2020 Lapo Luchini <lapo@lapo.it>
|
||||
|
||||
// Permission to use, copy, modify, and/or distribute this software for any
|
||||
// purpose with or without fee is hereby granted, provided that the above
|
||||
// copyright notice and this permission notice appear in all copies.
|
||||
//
|
||||
// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
// WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
// MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
// ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
// WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
||||
// ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
|
||||
// OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
|
||||
(typeof define != 'undefined' ? define : function (factory) { 'use strict';
|
||||
if (typeof module == 'object') module.exports = factory();
|
||||
else window.int10 = factory();
|
||||
})(function () {
|
||||
"use strict";
|
||||
|
||||
var max = 10000000000000; // biggest 10^n integer that can still fit 2^53 when multiplied by 256
|
||||
|
||||
/**
|
||||
* Arbitrary length base-10 value.
|
||||
* @param {number} value - Optional initial value (will be 0 otherwise).
|
||||
*/
|
||||
function Int10(value) {
|
||||
this.buf = [+value || 0];
|
||||
}
|
||||
|
||||
/**
|
||||
* Multiply value by m and add c.
|
||||
* @param {number} m - multiplier, must be < =256
|
||||
* @param {number} c - value to add
|
||||
*/
|
||||
Int10.prototype.mulAdd = function (m, c) {
|
||||
// assert(m <= 256)
|
||||
var b = this.buf,
|
||||
l = b.length,
|
||||
i, t;
|
||||
for (i = 0; i < l; ++i) {
|
||||
t = b[i] * m + c;
|
||||
if (t < max)
|
||||
c = 0;
|
||||
else {
|
||||
c = 0|(t / max);
|
||||
t -= c * max;
|
||||
}
|
||||
b[i] = t;
|
||||
}
|
||||
if (c > 0)
|
||||
b[i] = c;
|
||||
};
|
||||
|
||||
/**
|
||||
* Subtract value.
|
||||
* @param {number} c - value to subtract
|
||||
*/
|
||||
Int10.prototype.sub = function (c) {
|
||||
var b = this.buf,
|
||||
l = b.length,
|
||||
i, t;
|
||||
for (i = 0; i < l; ++i) {
|
||||
t = b[i] - c;
|
||||
if (t < 0) {
|
||||
t += max;
|
||||
c = 1;
|
||||
} else
|
||||
c = 0;
|
||||
b[i] = t;
|
||||
}
|
||||
while (b[b.length - 1] === 0)
|
||||
b.pop();
|
||||
};
|
||||
|
||||
/**
|
||||
* Convert to decimal string representation.
|
||||
* @param {*} base - optional value, only value accepted is 10
|
||||
*/
|
||||
Int10.prototype.toString = function (base) {
|
||||
if ((base || 10) != 10)
|
||||
throw 'only base 10 is supported';
|
||||
var b = this.buf,
|
||||
s = b[b.length - 1].toString();
|
||||
for (var i = b.length - 2; i >= 0; --i)
|
||||
s += (max + b[i]).toString().substring(1);
|
||||
return s;
|
||||
};
|
||||
|
||||
/**
|
||||
* Convert to Number value representation.
|
||||
* Will probably overflow 2^53 and thus become approximate.
|
||||
*/
|
||||
Int10.prototype.valueOf = function () {
|
||||
var b = this.buf,
|
||||
v = 0;
|
||||
for (var i = b.length - 1; i >= 0; --i)
|
||||
v = v * max + b[i];
|
||||
return v;
|
||||
};
|
||||
|
||||
/**
|
||||
* Return value as a simple Number (if it is <= 10000000000000), or return this.
|
||||
*/
|
||||
Int10.prototype.simplify = function () {
|
||||
var b = this.buf;
|
||||
return (b.length == 1) ? b[0] : this;
|
||||
};
|
||||
|
||||
return Int10;
|
||||
|
||||
});
|
||||
+2552
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,23 @@
|
||||
-----BEGIN PGP SIGNED MESSAGE-----
|
||||
Hash: SHA256
|
||||
|
||||
e150b18e296f1a09bd4e6837d1bc4197c8a0f5b130c4f21bbeb3b00c04575201 asn1.js
|
||||
340a46c0ac99d41fc780da48c15470073657aaf2530bd5b82e3589ce6b85ca41 oids.js
|
||||
beda29c0d41c756f06ad67d3b963ab10b06837d44f94f81eafd5d4d5a22c68a1 base64.js
|
||||
f82e6b96bbb1d3a693b8e124479996d4a06eba10104ad62b73cba5e2d10465ae hex.js
|
||||
e9ca034ce83e36a869fba33cfc26f6413f8383dbcfbf16c551e1c5bbf5835c5e int10.js
|
||||
e0ca0e8baa9f0ee823d606f25a5dd56400c9bbb8948df88768fd14e022aa2e1e dom.js
|
||||
a30ebd4fbb4fef0355d4c0ee78d3ca0092c6300b5b51c265392ac393d288ef50 test.js
|
||||
5095d30e2560fcead83071b856f94dbf05b9c59da38a5b18ab53a6491a75b4dd index.css
|
||||
ccc2330473b54c431010e41cdf219d18e96559452f2ab6f1fa7deb6df0aa5d34 index.js
|
||||
402c64f4f261b884337017834cf27f3c7590a9a6c36f1dd3d1b427ff284d1c4f index.html
|
||||
147802bfcd6aa22710fcba401cbe0fc9f458361a33c9d360862440aaf5b4ad4d README.md
|
||||
f4d552669aba9c9959a6fbfdbc66eb20f857e6efd4a42b19cb82131ea5899eb3 LICENSE
|
||||
66a053f6feb4b04d9127e1574793d812f715c1868cc31f228e5aff06946cc247 update.sh
|
||||
2b5f37ffafc4fe09331ed1f980afb46bcd515de536e0c5e4e0e8c0f5b5a626a1 check.sh
|
||||
-----BEGIN PGP SIGNATURE-----
|
||||
|
||||
iF0EAREIAB0WIQTUpSPQe+p0u9IYREdomIIsyPJS+wUCYXFUsQAKCRBomIIsyPJS
|
||||
+20kAJ0UcI5XFZAvQdCBdeq2BB0b0ITDwgCgs+Sfe13q/wUqqfCQoMQi/38QOQI=
|
||||
=+MOY
|
||||
-----END PGP SIGNATURE-----
|
||||
@@ -0,0 +1,86 @@
|
||||
#!/usr/bin/env node
|
||||
'use strict';
|
||||
|
||||
var Hex = require('./hex.js'),
|
||||
ASN1 = require('./asn1.js'),
|
||||
tests;
|
||||
|
||||
tests = [
|
||||
// http://luca.ntop.org/Teaching/Appunti/asn1.html
|
||||
['0304066E5DC0', '(18 bit)\n011011100101110111', 'Bit string: DER encoding'],
|
||||
['0304066E5DE0', '(18 bit)\n011011100101110111', 'Bit string: padded with "100000"'],
|
||||
['038104066E5DC0', '(18 bit)\n011011100101110111', 'Bit string: long form of length octets'],
|
||||
['0304086E5DC0', 'Exception:\nInvalid BitString with unusedBits=8', 'Bit string: invalid unusedBits'],
|
||||
['23090303006E5D030206C0', '(18 bit)\n011011100101110111', 'Bit string (constructed encoding): "0110111001011101" + "11"'],
|
||||
['04080123456789ABCDEF', '(8 byte)\n0123456789ABCDEF', 'Octet string: DER encoding'],
|
||||
['0481080123456789ABCDEF', '(8 byte)\n0123456789ABCDEF', 'Octet string: long form of length octets'],
|
||||
['240C040401234567040489ABCDEF', '(8 byte)\n0123456789ABCDEF', 'Octet string (constructed encoding): 01…67 + 89…ef'],
|
||||
// http://msdn.microsoft.com/en-us/library/windows/desktop/aa379076(v=vs.85).aspx
|
||||
['30820319308202820201003023310F300D0603550403130654657374434E3110300E060355040A1307546573744F726730819F300D06092A864886F70D010101050003818D00308189028181008FE2412A08E851A88CB3E853E7D54950B3278A2BCBEAB54273EA0257CC6533EE882061A11756C12418E3A808D3BED931F3370B94B8CC43080B7024F79CB18D5DD66D82D0540984F89F970175059C89D4D5C91EC913D72A6B309119D6D442E0C49D7C9271E1B22F5C8DEEF0F1171ED25F315BB19CBC2055BF3A37424575DC90650203010001A08201B4301A060A2B0601040182370D0203310C160A362E302E353336312E323042060A2B0601040182370D0201313430321E260043006500720074006900660069006300610074006500540065006D0070006C0061007400651E080055007300650072305706092B0601040182371514314A30480201090C237669636833642E6A646F6D6373632E6E74746573742E6D6963726F736F66742E636F6D0C154A444F4D4353435C61646D696E6973747261746F720C07636572747265713074060A2B0601040182370D0202316630640201011E5C004D006900630072006F0073006F0066007400200045006E00680061006E006300650064002000430072007900700074006F0067007200610070006800690063002000500072006F00760069006400650072002000760031002E003003010030818206092A864886F70D01090E31753073301706092B0601040182371402040A1E08005500730065007230290603551D2504223020060A2B0601040182370A030406082B0601050507030406082B06010505070302300E0603551D0F0101FF0404030205A0301D0603551D0E041604143C0F73DAF8EF41D83AEABE922A5D2C966A7B9454300D06092A864886F70D01010505000381810047EB995ADF9E700DFBA73132C15F5C24C2E0BFC624AF15660EB86A2EAB2BC4971FE3CBDC63A525ECC7B428616636A1311BBFDDD0FCBF1794901DE55EC7115EC9559FEBA33E14C799A6CBBAA1460F39D444C4C84B760E205D6DA9349ED4D58742EB2426511490B40F065E5288327A9520A0FDF7E57D60DD72689BF57B058F6D1E',
|
||||
'(3 elem)', 'PKCS#10 request'],
|
||||
// Int10
|
||||
['02102FA176B36EE9F049F444B40099661945', '(126 bit)\n63312083136615639753586560173617846597', 'Big integer (126 bit)'],
|
||||
['028181008953097086EE6147C5F4D5FFAF1B498A3D11EC5518E964DC52126B2614F743883F64CA51377ABB530DFD20464A48BD67CD27E7B29AEC685C5D10825E605C056E4AB8EEA460FA27E55AA62C498B02D7247A249838A12ECDF37C6011CF4F0EDEA9CEE687C1CB4A51C6AE62B2EFDB000723A01C99D6C23F834880BA8B42D5414E6F',
|
||||
'(1024 bit)\n96432446964907009840023644401994013457468837455140331578268642517697945390319089463541388080569398374873228752921897678940332050406994011437231634303608704223145390228074087922901239478374991949372306413157758278029522534299413919735715864599284769202556071242381348472464716517735026291259010477833523908207',
|
||||
'Big integer (1024 bit)'],
|
||||
['02820201009BA9ABBF614A97AF2F97669A745FD0D996FDCFE2E466EF1F1F4733C244A3DF9ADE1FB554DD157C6935116FBBC80C8E6A181ED88FD916BC1048365CF063B3905A5C2437D7A3D6CB0971B9F1017284B07DDB4D80CDFCD36FC9F8DAB60E82D24585A81B68A83DE8F4446CBDA1C2CB03BE8C3E130084DF4A48C0E3220AE8E937A7184CB1090D23567F044DD9178418A5C8DA409473EBCE0E573C03813A9D0AA1574369AC576D799078E5B5B43BD8BC4C8D28A1A7A3A7BA024E25D12AAEEDAE0322B86B200F302854957FE0EECE0A669DD1402D6E22AF9D1AC10519D26FC0F29FF87BB30242FB50A91D2D930F23ABC6C10F92FFD0A215F55309711CFF451384E6265EF8E0881C0AFC16B6A87306B8F0638402A0C65AECE774DF70AEA38325EAD6C7978793A7C68A8A33976037103E973E6E2915D6A10FD1882C129F6FAAA4C642EB41A2E39543D301856D8EBB3BF32336C7FE3BE0A1250748ABC98974FF088F80BFC09665F3EEEC4B68BD9D88C331B340F1E8CFF638BB9CE4D17FD4E5589B7CFAD4F30E9B7591E4BA522E197ED1F5CD5A19FCBA06F6FB52A84B9904DDF8F9B48B50A34E6289F08724FA8342C187FAD52D292A5A717A646AD72760630DDBCE49F58D1F90893217F87343B8D25A938661D6E1750AEA796676884F71EB0425D60A5A7A93E5B94B17400FB1B6B9F5DE4FDCE0B3AC3B117060844A436E9920C029710AC065',
|
||||
'(4096 bit)\n635048724432704421127930570668665246853305382538324205739741643121831497295424070220821366244137115920753022123888627038218427491681054376713237422498116573180444839575827154645186734602336866679804832661256616738257119870932328599495025506292424741581222812593482590762754785441060866630543522468678295806775919446210955958208696766307578451905771148370694894591388931494246786732600822191966681852303750991082312180670980233382216493445574638820565887523903118457551295241540793541306271618874366356869335229283992012581380459991160410157116077111142487644315609688092841697874946124416376553323373756926990721842430477982958383467149331238064901788481621489266725616974850293388387825359434286033332681714766010619113405542747712973535303497912234899589502990216128180823653963322406352206636893824027962569732222882297210841939793442415179615290739900774082858983244011679281115202763730964934473392333219986431517733237277686866318351054204026883453068392486990840498271719737813876367239342153571643327128417739316281558041652406500713712661305061745568036561978158652008943224271511931676512028205883718704503533046383542018858616087454820845906934069146870330990447993387221061968484774662499598623702280426558025111180066917',
|
||||
'Big integer (4096 bit)'],
|
||||
['0202007F', '127', 'Padded 127'],
|
||||
['0202FF7F', '-129', 'Negative 129'],
|
||||
['0202FC18', '-1000', 'Negative 1000 (2)'],
|
||||
['0204FFFFFC18', '-1000', 'Negative 1000 (4)'],
|
||||
['0208FFFFFFFFFFFFFC18', '-1000', 'Negative 1000 (8)'],
|
||||
['0210FFFFFFFFFFFFFFFFFFFFFFFFFFFFFC18', '-1000', 'Negative 1000 (16)'],
|
||||
['0203800001', '-8388607', 'Negative 8388607'],
|
||||
['02020000', '0', 'Zero (2)'],
|
||||
['0204FFFFFFFF', '-1', 'Negative 1 (4)'],
|
||||
// OID
|
||||
['060C69C7C79AB78084C289F9870D', '2.25.84478768945400492475277', 'Big OID arc'],
|
||||
['06146982968D8D889BCCA8C7B3BDD4C080AAAED78A1B', '2.25.184830721219540099336690027854602552603', 'Bigger OID arc'],
|
||||
['060488378952', '2.999.1234', 'OID arc > 2.47'],
|
||||
['060782A384F3CAC00A', '2.9999999999930', 'OID with Int10 corner case (1)'],
|
||||
['060881E3AFEAA69A800A', '2.999999999999930', 'OID with Int10 corner case (2)'],
|
||||
['06092A864886F70D010105', '1.2.840.113549.1.1.5\nsha1WithRSAEncryption\nPKCS #1', 'known OID from Peter Gutmann list'],
|
||||
// OID corner case from https://misc.daniel-marschall.de/asn.1/oid-sizecheck/oid_size_test.txt
|
||||
['060A81FFFFFFFFFFFFFFFF7F', '2.18446744073709551535', 'OID root 64 bit - 1'],
|
||||
['060A82808080808080808000', '2.18446744073709551536', 'OID root 64 bit'],
|
||||
['060A82808080808080808001', '2.18446744073709551537', 'OID root 64 bit + 1'],
|
||||
['0620FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF7F', '2.26959946667150639794667015087019630673637144422540572481103610249135', 'OID derLen20c'],
|
||||
['0621818080808080808080808080808080808080808080808080808080808080808000', '2.26959946667150639794667015087019630673637144422540572481103610249136', 'OID derLen21c'],
|
||||
// UTF-8
|
||||
['0C0E4C61706FE280997320F09F9A972E', 'Lapo’s 🚗.', 'UTF-8 4-byte sequence'],
|
||||
// T-REC-X.690-201508
|
||||
['0307040A3B5F291CD0', '(44 bit)\n00001010001110110101111100101001000111001101', 'Example 8.6.4.2: bit string (primitive encoding)'],
|
||||
['23800303000A3B0305045F291CD00000', '(44 bit)\n00001010001110110101111100101001000111001101', 'Example 8.6.4.2: bit string (constructed encoding)'],
|
||||
// avoid past bugs
|
||||
['23800303000A3B230A0302005F030404291CD00000', '(44 bit)\n00001010001110110101111100101001000111001101', 'Bit string (recursive constructed)'],
|
||||
['0348003045022100DE601E573DAFB59BC551D58E3E7B9EDA0612DD0112805A2217B734759B884417022067C3FDE60780D41C1D7A3B90291F3D39C4DC2F206DCCBA2F982C06B67C09B232', '(568 bit)\n0011000001000101000000100010000100000000110111100110000000011110010101110011110110101111101101011001101111000101010100011101010110001110001111100111101110011110110110100000011000010010110111010000000100010010100000000101101000100010000101111011011100110100011101011001101110001000010001000001011100000010001000000110011111000011111111011110011000000111100000001101010000011100000111010111101000111011100100000010100100011111001111010011100111000100110111000010111100100000011011011100110010111010001011111001100000101100000001101011011001111100000010011011001000110010', 'not constructed, but contains structures'],
|
||||
['040731323334353637', '(7 byte)\n1234567', 'Octet string with ASCII content'],
|
||||
['0407312E3233E282AC', '(7 byte)\n1.23€', 'Octet string with UTF-8 content'],
|
||||
['0420041EE4E3B7ED350CC24D034E436D9A1CB15BB1E328D37062FB82E84618AB0A3C', '(32 byte)\n041EE4E3B7ED350CC24D034E436D9A1CB15BB1E328D37062FB82E84618AB0A3C', 'Do not mix encapsulated and structured octet strings'], // GitHub issue #47
|
||||
];
|
||||
|
||||
var run = 0,
|
||||
error = 0;
|
||||
tests.forEach(function (t) {
|
||||
var input = t[0],
|
||||
expected = t[1],
|
||||
comment = t[2],
|
||||
result = null;
|
||||
try {
|
||||
result = ASN1.decode(Hex.decode(input)).content();
|
||||
//TODO: check structure, not only first level content
|
||||
} catch (e) {
|
||||
result = 'Exception:\n' + e;
|
||||
}
|
||||
++run;
|
||||
if (result == expected)
|
||||
console.log('\x1B[1m\x1B[32mOK \x1B[39m\x1B[22m ' + comment);
|
||||
else {
|
||||
++error;
|
||||
console.log('\x1B[1m\x1B[31mERR\x1B[39m\x1B[22m ' + comment + '\n' + result);
|
||||
}
|
||||
});
|
||||
console.log('Errors: ' + error + '/' + run + '.');
|
||||
process.exit(error ? 1 : 0);
|
||||
@@ -0,0 +1,56 @@
|
||||
#/bin/sh
|
||||
URL='https://www.cs.auckland.ac.nz/~pgut001/dumpasn1.cfg'
|
||||
if [ -x /usr/bin/fetch ]; then
|
||||
/usr/bin/fetch -m --no-verify-peer $URL
|
||||
elif [ -x /usr/bin/wget ]; then
|
||||
/usr/bin/wget -N --no-check-certificate $URL
|
||||
elif [ ! -r dumpasn1.cfg ]; then
|
||||
echo Please download $URL in this directory.
|
||||
exit 1
|
||||
fi
|
||||
cat dumpasn1.cfg | \
|
||||
tr -d '\r' | \
|
||||
awk -v url="$URL" '
|
||||
function clean() {
|
||||
oid = "";
|
||||
comment = "";
|
||||
description = "";
|
||||
warning = "";
|
||||
}
|
||||
BEGIN {
|
||||
FS = "= *";
|
||||
apos = sprintf("%c", 39);
|
||||
clean();
|
||||
print "// Converted from: " url;
|
||||
print "// which is made by Peter Gutmann and whose license states:";
|
||||
print "// You can use this code in whatever way you want,";
|
||||
print "// as long as you don" apos "t try to claim you wrote it.";
|
||||
print "(typeof define != " apos "undefined" apos " ? define : function (factory) { " apos "use strict" apos ";";
|
||||
print " if (typeof module == " apos "object" apos ") module.exports = factory();";
|
||||
print " else window.oids = factory();";
|
||||
print "})(function () {";
|
||||
print apos "use strict" apos ";";
|
||||
print "return {";
|
||||
}
|
||||
/^OID/ { oid = $2; }
|
||||
/^Comment/ { comment = $2; }
|
||||
/^Description/ { description = $2; }
|
||||
/^Warning/ { warning = ", \"w\": true"; }
|
||||
/^$/ {
|
||||
if (length(oid) > 0) {
|
||||
gsub(" ", ".", oid);
|
||||
gsub("\"", "\\\"", description);
|
||||
gsub("\"", "\\\"", comment);
|
||||
if (++seen[oid] > 1)
|
||||
print "Duplicate OID in line " NR ": " oid > "/dev/stderr";
|
||||
else
|
||||
printf "\"%s\": { \"d\": \"%s\", \"c\": \"%s\"%s },\n", oid, description, comment, warning;
|
||||
clean();
|
||||
}
|
||||
}
|
||||
END {
|
||||
print "\"END\": \"\""
|
||||
print "};});"
|
||||
}
|
||||
' >oids.js
|
||||
echo Conversion completed.
|
||||
Vendored
+339
@@ -0,0 +1,339 @@
|
||||
function check(v, re, msg) {
|
||||
if (!re.test(v)) {
|
||||
alert(msg)
|
||||
}
|
||||
}
|
||||
|
||||
function padPkcs7(data) {
|
||||
|
||||
var d = data.length % 16;
|
||||
d = 16 - d;
|
||||
var arr = Array.from(data)
|
||||
for (var i = 0; i < d; i++) {
|
||||
arr.push(d)
|
||||
}
|
||||
return arr;
|
||||
}
|
||||
|
||||
function stripPcks7(data) {
|
||||
var arr = Array.from(data)
|
||||
var padder = arr[arr.length - 1];
|
||||
return arr.slice(0, arr.length - padder);
|
||||
}
|
||||
|
||||
function ecb(bytes, cb) {
|
||||
var ret = []
|
||||
for (var i = 0; i < bytes.length; i += 16) {
|
||||
var d = bytes.slice(i, i + 16);
|
||||
var en = cb(d)
|
||||
ret = ret.concat(Array.from(en))
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
class ActiveEpc {
|
||||
constructor() {
|
||||
this.server = "ws://127.0.0.1:12321/active";
|
||||
this.waitMap = {}
|
||||
|
||||
}
|
||||
|
||||
__debug(...str) {
|
||||
if (window.active_debug) {
|
||||
console.log(...str)
|
||||
}
|
||||
}
|
||||
|
||||
connect() {
|
||||
this.__debug("connect")
|
||||
var _this = this;
|
||||
try {
|
||||
|
||||
if (this.sock) {
|
||||
this.sock.onclose = function () {
|
||||
}
|
||||
this.sock.close()
|
||||
}
|
||||
|
||||
this.sock = new WebSocket(this.server);
|
||||
this.__debug("sock")
|
||||
this.sock.onopen = function () {
|
||||
_this.__debug("open");
|
||||
_this.sock.isopened = true;
|
||||
_this.sock.onmessage = function (e) {
|
||||
_this.__debug(e.data)
|
||||
var ret = JSON.parse(e.data);
|
||||
|
||||
var cb = _this.waitMap[ret.id]
|
||||
cb && cb(ret)
|
||||
}
|
||||
};
|
||||
|
||||
this.sock.onclose = function () {
|
||||
_this.sock.isopened = false;
|
||||
_this.__debug("close");
|
||||
_this.reconnect();
|
||||
};
|
||||
|
||||
// this.sock.onerror = function () {
|
||||
// _this.sock.isopened = false;
|
||||
// this.__debug("onerror");
|
||||
// _this.reconnect();
|
||||
// };
|
||||
|
||||
} catch (e) {
|
||||
_this.__debug("onerror");
|
||||
_this.reconnect();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
reconnect() {
|
||||
this.__debug("reconnect")
|
||||
var _this = this;
|
||||
|
||||
if (_this.sock && _this.sock.isopened) {
|
||||
this.__debug("miss")
|
||||
return
|
||||
}
|
||||
|
||||
setTimeout(function () {
|
||||
_this.connect();
|
||||
}, 3000);
|
||||
}
|
||||
|
||||
__send(cmd, param, cb) {
|
||||
var id = (Math.random() + "").substr(2);
|
||||
this.sock.send(
|
||||
JSON.stringify({
|
||||
id: id,
|
||||
cmd: cmd,
|
||||
param: param
|
||||
})
|
||||
);
|
||||
if (cb) {
|
||||
this.waitMap[id] = cb;
|
||||
}
|
||||
}
|
||||
|
||||
__check(v, re, msg, reject) {
|
||||
if (!re.test(v)) {
|
||||
reject && reject({
|
||||
msg,
|
||||
code: "C0"
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
login(uid, utype, pwd) {
|
||||
var _this = this;
|
||||
return new Promise(function (resolve, reject) {
|
||||
|
||||
if (!_this.sock.isopened) {
|
||||
reject({
|
||||
code: "CB",
|
||||
msg: "Active 通信失败"
|
||||
})
|
||||
}
|
||||
|
||||
_this.__check(uid, /\d{1,2}/g, "用户编号填写错误!", reject);
|
||||
_this.__check(utype, /\d{1}/g, "用户类型填写错误!", reject);
|
||||
_this.__check(pwd, /\d{6}/g, "密码填写错误!", reject);
|
||||
|
||||
_this.__send("login", {
|
||||
uid, utype, pwd
|
||||
}, function (ret) {
|
||||
if (ret.code === "00" || ret.code === "33") {
|
||||
resolve(ret)
|
||||
} else {
|
||||
reject(ret)
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
logout() {
|
||||
var _this = this;
|
||||
return new Promise(function (resolve, reject) {
|
||||
|
||||
if (!_this.sock.isopened) {
|
||||
reject({
|
||||
code: "CB",
|
||||
msg: "Active 通信失败"
|
||||
})
|
||||
}
|
||||
|
||||
_this.__send("logout", {}, function (ret) {
|
||||
if (ret.code === "00" || ret.code === "2E") {
|
||||
resolve(ret)
|
||||
} else {
|
||||
reject(ret)
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
getSn() {
|
||||
var _this = this;
|
||||
return new Promise(function (resolve, reject) {
|
||||
|
||||
if (!_this.sock.isopened) {
|
||||
reject({
|
||||
code: "CB",
|
||||
msg: "Active 通信失败"
|
||||
})
|
||||
}
|
||||
|
||||
_this.__send("getSn", {}, function (ret) {
|
||||
if (ret.code === "00") {
|
||||
resolve(ret)
|
||||
} else {
|
||||
reject(ret)
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
setAutoSleepTime(minutes) {
|
||||
var _this = this;
|
||||
return new Promise(function (resolve, reject) {
|
||||
|
||||
_this.__check(minutes, /\d{1,2}/g, "时间填写错误!", reject);
|
||||
|
||||
var v = parseInt(minutes, 10);
|
||||
if( v > 20 || v < 2 ) {
|
||||
reject({
|
||||
code : "C0",
|
||||
msg: "时间超出范围"
|
||||
})
|
||||
}
|
||||
|
||||
if (!_this.sock.isopened) {
|
||||
reject({
|
||||
code: "CB",
|
||||
msg: "Active 通信失败"
|
||||
})
|
||||
}
|
||||
|
||||
_this.__send("setAutoSleepTime", { minutes }, function (ret) {
|
||||
if (ret.code === "00") {
|
||||
resolve(ret)
|
||||
} else {
|
||||
reject(ret)
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
|
||||
modifyPassword(uid, utype, pwd) {
|
||||
var _this = this;
|
||||
|
||||
return new Promise(function (resolve, reject) {
|
||||
|
||||
if (!_this.sock.isopened) {
|
||||
reject({
|
||||
code: "CB",
|
||||
msg: "Active 通信失败"
|
||||
})
|
||||
}
|
||||
|
||||
_this.__check(uid, /\d{1,2}/g, "用户编号填写错误!", reject);
|
||||
_this.__check(utype, /\d{1}/g, "用户类型填写错误!", reject);
|
||||
_this.__check(pwd, /\d{6}/g, "密码填写错误!", reject);
|
||||
|
||||
_this.__send("modifyPassword", {
|
||||
uid, utype, pwd
|
||||
}, function (ret) {
|
||||
if (ret.code === "00") {
|
||||
resolve(ret)
|
||||
} else {
|
||||
reject(ret)
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
calcPaycode(accr, accu, ticketType, ticketNo, date, banlance) {
|
||||
var _this = this;
|
||||
|
||||
return new Promise(function (resolve, reject) {
|
||||
|
||||
if (!_this.sock.isopened) {
|
||||
reject({
|
||||
code: "CB",
|
||||
msg: "Active 通信失败"
|
||||
})
|
||||
}
|
||||
|
||||
|
||||
|
||||
_this.__check(accu, /\d{1,32}/g, "收方账户填写错误!", reject);
|
||||
_this.__check(ticketType, /\d{1}/g, "票据类型填写错误!", reject);
|
||||
_this.__check(ticketNo, /\d{1,8}/g, "票据编号填写错误!", reject);
|
||||
_this.__check(date, /^(?:(?:1[6-9]|[2-9][0-9])[0-9]{2}([-/.]?)(?:(?:0?[1-9]|1[0-2])\1(?:0?[1-9]|1[0-9]|2[0-8])|(?:0?[13-9]|1[0-2])\1(?:29|30)|(?:0?[13578]|1[02])\1(?:31))|(?:(?:1[6-9]|[2-9][0-9])(?:0[48]|[2468][048]|[13579][26])|(?:16|[2468][048]|[3579][26])00)([-/.]?)0?2\2(?:29))$/g, "时间填写错误!", reject);
|
||||
_this.__check(banlance, /\d{1,16}/g, "金额填写错误!", reject);
|
||||
if ( '4' == ticketType || '5' == ticketType ) {
|
||||
if ( undefined === accr || "" === accr ) {
|
||||
reject({
|
||||
code: "C0",
|
||||
msg: "票据类型为汇兑和其他时,收方账号必填。"
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
if ( undefined === accr ) {
|
||||
accr = ""
|
||||
}
|
||||
|
||||
_this.__send("calcPaycode", {
|
||||
accr, accu, ticketType, ticketNo, date, banlance
|
||||
}, function (ret) {
|
||||
if (ret.code === "00") {
|
||||
resolve(ret)
|
||||
} else {
|
||||
reject(ret)
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
getAccountList() {
|
||||
var _this = this;
|
||||
return new Promise(function (resolve, reject) {
|
||||
if (!_this.sock.isopened) {
|
||||
reject({
|
||||
code: "CB",
|
||||
msg: "Active 通信失败"
|
||||
})
|
||||
}
|
||||
_this.__send("getAccountList", {}, function (ret) {
|
||||
if (ret.code === "00") {
|
||||
resolve(ret)
|
||||
} else {
|
||||
reject(ret)
|
||||
}
|
||||
})
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* 检测通过返回 true
|
||||
* 检测不通过返回 fase
|
||||
*/
|
||||
ActiveEpc.checkSupport = function () {
|
||||
try {
|
||||
if (!!window.WebSocket && window.WebSocket.prototype.send) {
|
||||
return true;
|
||||
} else {
|
||||
console.error("您的浏览器不支持!")
|
||||
return false;
|
||||
}
|
||||
} catch (e) {
|
||||
console.error("当前环境不支持!", e)
|
||||
return false;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,401 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>无线支付密码器 js 接口示例</title>
|
||||
<style>
|
||||
body {
|
||||
width: 430px;
|
||||
overflow-x: hidden;
|
||||
color: sienna;
|
||||
}
|
||||
|
||||
|
||||
.step {
|
||||
margin: 1rem;
|
||||
border: silver dashed 1px;
|
||||
padding: 0 1rem 1rem 1rem;
|
||||
border-radius: 1rem;
|
||||
}
|
||||
|
||||
.loading{
|
||||
width: 80px;
|
||||
height: 40px;
|
||||
margin: 0 auto;
|
||||
margin-top:100px;
|
||||
}
|
||||
.loading span{
|
||||
display: inline-block;
|
||||
width: 8px;
|
||||
height: 100%;
|
||||
border-radius: 4px;
|
||||
background: lightgreen;
|
||||
-webkit-animation: load 1s ease infinite;
|
||||
}
|
||||
@-webkit-keyframes load{
|
||||
0%,100%{
|
||||
height: 40px;
|
||||
background: lightgreen;
|
||||
}
|
||||
50%{
|
||||
height: 70px;
|
||||
margin: -15px 0;
|
||||
background: lightblue;
|
||||
}
|
||||
}
|
||||
.loading span:nth-child(2){
|
||||
-webkit-animation-delay:0.2s;
|
||||
}
|
||||
.loading span:nth-child(3){
|
||||
-webkit-animation-delay:0.4s;
|
||||
}
|
||||
.loading span:nth-child(4){
|
||||
-webkit-animation-delay:0.6s;
|
||||
}
|
||||
.loading span:nth-child(5){
|
||||
-webkit-animation-delay:0.8s;
|
||||
}
|
||||
</style>
|
||||
<link href="layx.min.css" rel="stylesheet" type="text/css" />
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<div id="title-warning" style="width: 100%; color:#f3b223; font-size: 2rem ;text-align: center"><span>您的浏览器不支持! </span></div>
|
||||
|
||||
<div style="text-align: center"><h2>功能测试</h2></div>
|
||||
|
||||
<div class="step">
|
||||
<h3>基本功能</h3>
|
||||
|
||||
<div style="margin-bottom: 1rem">
|
||||
|
||||
<div style="margin-bottom: 1rem">
|
||||
<div style="margin-bottom: 1rem; display: inline-block; margin-right: 1rem">当前状态: <span id="status">....</span>    <button id="logout">退  出</button></div>
|
||||
|
||||
<div style="margin-bottom: 1rem">
|
||||
<input id="uid" type="text" maxlength="2" placeholder="用户编号,1~2 个数字">
|
||||
<select id="utype" style="height: 1.2rem">
|
||||
<option value ="0">法人/授权人</option>
|
||||
<option value ="1">主管/主管</option>
|
||||
<option value ="2">会计/审核人</option>
|
||||
<option value ="3">出纳/签发人</option>
|
||||
</select>
|
||||
</div>
|
||||
<div style="margin-bottom: 1rem">
|
||||
<input id="pwd1" type="password" maxlength="6" placeholder="口令,6 个数字">
|
||||
<button id="login" style="margin-right: 1rem">登  录</button></div>
|
||||
</div>
|
||||
|
||||
|
||||
</div>
|
||||
<div><input id="pwd2" type="password" maxlength="6" placeholder="6 个数字"> <button id="modifyPassword">修改口令</button> </div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<div class="step">
|
||||
<h3>获取设备编号</h3>
|
||||
<div>设备编号: <input id="sn" readonly type="text"></div>
|
||||
<button id="getSn" style="margin-top:1rem; margin-left: 0rem;">获取</button>
|
||||
</div>
|
||||
|
||||
<div class="step">
|
||||
<h3>设置自动休眠时间</h3>
|
||||
<div>分钟: <input id="minutes" type="text" maxlength="2"></div>
|
||||
<button id="setAutoSleepTime" style="margin-top:1rem; margin-left: 0rem;">设置</button>
|
||||
</div>
|
||||
|
||||
<div class="step">
|
||||
<h3>支付密码计算</h3>
|
||||
<div>收方账户: <input type="text" id="accr" maxlength="30" placeholder="30 个数字,汇兑凭证/其他必填"></div>
|
||||
<div>付方账户: <input type="text" id="accu" maxlength="32" placeholder="8 ~ 32 个数字"></div>
|
||||
<div>票据类型: <select id="ticketType" style="height: 1.2rem">
|
||||
<option value ="1">支票</option>
|
||||
<option value ="2">银行汇票</option>
|
||||
<option value ="3">银行本票</option>
|
||||
<option value ="4">汇兑凭证</option>
|
||||
<option value ="5">其他</option>
|
||||
</select>
|
||||
</div>
|
||||
<div>票据编号: <input id="ticketNo" type="text" maxlength="8" placeholder="最大 8 个数字"></div>
|
||||
<div>时  间: <input id="date" type="text" maxlength="8" placeholder="yyyyMMdd"></div>
|
||||
<div>金  额: <input id="banlance" type="text" maxlength="16" placeholder="最大 16 个数字,单位是“分”"></div>
|
||||
<div>支付密码: <input id="paycode" readonly type="text"></div>
|
||||
<button id="calcPaycode" style="margin-top:1rem; margin-left: 0rem;">计算支付密码</button>
|
||||
</div>
|
||||
|
||||
|
||||
|
||||
<div class="step">
|
||||
<h3>获取账户列表</h3>
|
||||
<button id="getAccountList">获取所有账户</button> <span style="color: silver; font-size: 0.8rem">账户比较多时较慢,最长 30 秒。</span>
|
||||
|
||||
<div id="loadding-account-list" class="loading" style="margin-bottom: 2rem">
|
||||
<span></span>
|
||||
<span></span>
|
||||
<span></span>
|
||||
<span></span>
|
||||
<span></span>
|
||||
</div>
|
||||
<div id="account-list" style="margin-top: 1rem">
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<!-- 仅此示例程序需要依赖 jquery -->
|
||||
<script src="jquery.min.js"></script>
|
||||
<script src="layx.min.js" type="text/javascript"></script>
|
||||
|
||||
|
||||
<script src="active.epc.min.js"></script>
|
||||
<script type="application/javascript">
|
||||
|
||||
function getyyyyMMdd(){
|
||||
var d = new Date();
|
||||
var curr_date = d.getDate();
|
||||
var curr_month = d.getMonth() + 1;
|
||||
var curr_year = d.getFullYear();
|
||||
String(curr_month).length < 2 ? (curr_month = "0" + curr_month): curr_month;
|
||||
String(curr_date).length < 2 ? (curr_date = "0" + curr_date): curr_date;
|
||||
var yyyyMMdd = curr_year + "" + curr_month +""+ curr_date;
|
||||
return yyyyMMdd;
|
||||
}
|
||||
|
||||
// 覆盖默认行为
|
||||
function success(msg){
|
||||
layx.notice({
|
||||
title: '成功',
|
||||
type: 'success',
|
||||
message: msg
|
||||
});
|
||||
}
|
||||
|
||||
// 覆盖默认行为
|
||||
function warning(msg){
|
||||
layx.notice({
|
||||
title: '警告',
|
||||
type: 'warning',
|
||||
message: msg
|
||||
});
|
||||
}
|
||||
|
||||
// 覆盖默认行为
|
||||
function alert(msg){
|
||||
layx.notice({
|
||||
title: '错误',
|
||||
type: 'error',
|
||||
message: msg
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
|
||||
// init
|
||||
$("#title-warning").hide();
|
||||
$("#loadding-account-list").hide();
|
||||
$("#date").val( getyyyyMMdd() );
|
||||
|
||||
$(function () {
|
||||
if ( ! ActiveEpc.checkSupport() ) {
|
||||
$("#title-warning").show();
|
||||
} else {
|
||||
$("#title-warning").hide();
|
||||
}
|
||||
|
||||
|
||||
// 建立连接
|
||||
var api = new ActiveEpc();
|
||||
api.connect()
|
||||
|
||||
$("#login").click(function (){
|
||||
$(this).attr("disabled",true);
|
||||
// 用户登录
|
||||
var uid = $("#uid").val();
|
||||
var utype = $("#utype").val();
|
||||
var pwd1 = $("#pwd1").val();
|
||||
|
||||
api.login(uid, utype, pwd1)
|
||||
.then(function ( ret ){
|
||||
if ( ret.code === "00" ) {
|
||||
success("登录成功")
|
||||
} else {
|
||||
warning("重复登录")
|
||||
}
|
||||
|
||||
$("#status").text("已登录").css({ color : "green"});
|
||||
})
|
||||
.catch(function (e) {
|
||||
alert("[" + e.code + "]" + "登录失败," + (e.data ? "剩余尝试次数" + e.data : e.msg) )
|
||||
$("#status").text("...").css({ color : "sliver"})
|
||||
}).finally(() => {
|
||||
$(this).attr("disabled",false);
|
||||
})
|
||||
})
|
||||
|
||||
|
||||
$("#logout").click(function (){
|
||||
$(this).attr("disabled",true);
|
||||
api.logout()
|
||||
.then(function (ret){
|
||||
if ( ret.code === "00" ) {
|
||||
success("已退出")
|
||||
} else {
|
||||
warning("重复退出")
|
||||
}
|
||||
|
||||
$("#status").text("已退出").css({ color : "orange"})
|
||||
})
|
||||
.catch(function (e) {
|
||||
alert("[" + e.code + "]" + "退出失败," + e.msg)
|
||||
$("#status").text("...").css({ color : "orange"})
|
||||
}).finally(() => {
|
||||
$(this).attr("disabled",false);
|
||||
})
|
||||
})
|
||||
|
||||
$("#getSn").click(function (){
|
||||
api.getSn()
|
||||
.then(function ( ret ){
|
||||
success("获取芯片编号成功!")
|
||||
$("#sn").val( ret.data )
|
||||
})
|
||||
.catch(function (e) {
|
||||
alert("[" + e.code + "]" + "获取芯片编号失败," + e.msg)
|
||||
if ( "2E" === e.code ) {
|
||||
$("#status").text("未登录").css({ color : "sliver"})
|
||||
}
|
||||
}).finally(() => {
|
||||
$(this).attr("disabled",false);
|
||||
})
|
||||
})
|
||||
|
||||
$("#setAutoSleepTime").click(function (){
|
||||
var minutes = $("#minutes").val();
|
||||
api.setAutoSleepTime( minutes )
|
||||
.then(function ( ret ){
|
||||
success("设置自动休眠时间成功!")
|
||||
$("#minutes").val("")
|
||||
})
|
||||
.catch(function (e) {
|
||||
alert("[" + e.code + "]" + "设置自动休眠时间失败," + e.msg)
|
||||
if ( "2E" === e.code ) {
|
||||
$("#status").text("未登录").css({ color : "sliver"})
|
||||
}
|
||||
}).finally(() => {
|
||||
$(this).attr("disabled",false);
|
||||
})
|
||||
})
|
||||
|
||||
|
||||
|
||||
$("#modifyPassword").click(function (){
|
||||
|
||||
var uid = $("#uid").val();
|
||||
var utype = $("#utype").val();
|
||||
var pwd2 = $("#pwd2").val();
|
||||
|
||||
$(this).attr("disabled",true);
|
||||
api.modifyPassword(uid, utype, pwd2)
|
||||
.then(function (){
|
||||
success("密码修改成功,请牢记!")
|
||||
})
|
||||
.catch(function (e) {
|
||||
alert("[" + e.code + "]" + "修改密码失败," + e.msg)
|
||||
if ( "2E" === e.code ) {
|
||||
$("#status").text("未登录").css({ color : "sliver"})
|
||||
}
|
||||
|
||||
}).finally(() => {
|
||||
$(this).attr("disabled",false);
|
||||
})
|
||||
|
||||
})
|
||||
|
||||
$("#calcPaycode").click(function (){
|
||||
$(this).attr("disabled",true);
|
||||
|
||||
var accr = $("#accr").val();
|
||||
var accu = $("#accu").val();
|
||||
var ticketType = $("#ticketType").val();
|
||||
var ticketNo = $("#ticketNo").val();
|
||||
var date = $("#date").val();
|
||||
var banlance = $("#banlance").val();
|
||||
|
||||
api.calcPaycode(accr, accu, ticketType, ticketNo, date, banlance)
|
||||
.then(function (ret){
|
||||
var v = ret.data;
|
||||
if ( v.startsWith("FFFF") ) {
|
||||
v = v.substr(4);
|
||||
}
|
||||
$("#paycode").val(v);
|
||||
success("计算结束")
|
||||
})
|
||||
.catch(function (e) {
|
||||
$("#paycode").val("");
|
||||
alert("[" + e.code + "]" + "计算支付密码失败," + e.msg)
|
||||
if ( "2E" === e.code ) {
|
||||
$("#status").text("未登录").css({ color : "sliver"})
|
||||
}
|
||||
}).finally(() => {
|
||||
$(this).attr("disabled",false);
|
||||
})
|
||||
|
||||
})
|
||||
|
||||
$("#getAccountList").click(function (){
|
||||
|
||||
$(this).attr("disabled",true);
|
||||
$("#account-list").hide();
|
||||
$("#loadding-account-list").show();
|
||||
api.getAccountList()
|
||||
.then(function ( ret ){
|
||||
var data = ret.data;
|
||||
var table = " <table border=\"1\">\n" +
|
||||
" <tr>\n" +
|
||||
" <th>ID</th>\n" +
|
||||
" <th>账户</th>\n" +
|
||||
" <th>有效位</th>\n" +
|
||||
" </tr>\n" +
|
||||
"\n"
|
||||
|
||||
|
||||
for ( var i = 0; i < data.length; i++) {
|
||||
table += "<tr>\n" +
|
||||
" <td>"+ data[i].id +"</td>\n" +
|
||||
" <td>"+ data[i].acc +"</td>\n" +
|
||||
" <td>"+ data[i].len +"</td>\n" +
|
||||
" </tr>"
|
||||
}
|
||||
|
||||
+ " </table>"
|
||||
|
||||
|
||||
|
||||
$("#account-list").html( table ).show();
|
||||
})
|
||||
.catch(function (e) {
|
||||
alert("[" + e.code + "]" + "获取账号列表失败," + e.msg)
|
||||
if ( "2E" === e.code ) {
|
||||
$("#status").text("未登录").css({ color : "sliver"})
|
||||
}
|
||||
}).finally(() => {
|
||||
$("#loadding-account-list").hide();
|
||||
$(this).attr("disabled",false);
|
||||
})
|
||||
|
||||
})
|
||||
|
||||
})
|
||||
|
||||
|
||||
|
||||
|
||||
</script>
|
||||
|
||||
|
||||
|
||||
</body>
|
||||
</html>
|
||||
Vendored
+2
File diff suppressed because one or more lines are too long
Vendored
+1
File diff suppressed because one or more lines are too long
Vendored
+5
File diff suppressed because one or more lines are too long
+7
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,372 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
|
||||
|
||||
<!-- Bootstrap 的 CSS 文件 -->
|
||||
<link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/bootstrap@4.6.1/dist/css/bootstrap.min.css" crossorigin="anonymous">
|
||||
|
||||
<title>十字导航</title>
|
||||
|
||||
<style type="text/css">
|
||||
*{
|
||||
moz-user-select: -moz-none;
|
||||
-moz-user-select: none;
|
||||
-o-user-select:none;
|
||||
-khtml-user-select:none;
|
||||
-webkit-user-select:none;
|
||||
-ms-user-select:none;
|
||||
user-select:none;
|
||||
}
|
||||
|
||||
@font-face {
|
||||
font-family: 'iconfont'; /* Project id 3145309 */
|
||||
src: url('//at.alicdn.com/t/font_3145309_gmztz69c7.woff2?t=1642386884581') format('woff2'),
|
||||
url('//at.alicdn.com/t/font_3145309_gmztz69c7.woff?t=1642386884581') format('woff'),
|
||||
url('//at.alicdn.com/t/font_3145309_gmztz69c7.ttf?t=1642386884581') format('truetype');
|
||||
}
|
||||
|
||||
.iconfont {
|
||||
font-family: "iconfont" !important;
|
||||
font-size: 16px;
|
||||
font-style: normal;
|
||||
-webkit-font-smoothing: antialiased;
|
||||
-moz-osx-font-smoothing: grayscale;
|
||||
}
|
||||
|
||||
#canvas canvas {
|
||||
border: 1px dotted black
|
||||
}
|
||||
|
||||
.tooltip-inner{
|
||||
max-width: 400px !important;
|
||||
text-align: justify;
|
||||
}
|
||||
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
|
||||
<div class="container" style="text-align: center">
|
||||
|
||||
<div class="head" style="position: absolute; top: 2rem; right: 2rem">
|
||||
<div class="btn-group" role="group">
|
||||
<button onclick="addObj()" type="button" class="btn btn-primary"><span class="iconfont"></span>添加</button>
|
||||
<button onclick="clearObjs()" type="button" class="btn btn-danger"><span class="iconfont"></span>清空</button>
|
||||
</div>
|
||||
|
||||
<button type="button" class="btn btn-info" data-toggle="tooltip" data-placement="bottom" data-html="true"
|
||||
title="</br><ol><li>点击【添加】画板中会添加一个默认事件</li><li>右键事件可以修改</li><li>将事件修改为空会完全删除事件</li><li>刷新页面会丢失所有数据</li></ol>">帮助</button>
|
||||
|
||||
<div class="btn-group" role="group">
|
||||
<button onclick="imports()" type="button" class="btn btn-primary"><span class="iconfont"></span>导入
|
||||
<input style="display: none" type="file" accept=".crossnav.png" class="custom-file-input" id="custom-file-input">
|
||||
</button>
|
||||
<button onclick="outports()" type="button" class="btn btn-primary"><span class="iconfont"></span>导出</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div id="canvas" style="margin-top: 5rem;">
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
<!-- 图片 exif 操作 -->
|
||||
<script src="./exif.js"></script>
|
||||
|
||||
<!-- 选项 1:jQuery 和 Bootstrap 集成包(集成了 Popper) -->
|
||||
<script src="./jquery.slim.min.js" crossorigin="anonymous"></script>
|
||||
<script src="./bootstrap.bundle.min.js" crossorigin="anonymous"></script>
|
||||
|
||||
<!-- 动画库 -->
|
||||
<script src="../../js/pixi.min.js"></script>
|
||||
<script src="../../js/PIXI.TextInput.min.js"></script>
|
||||
|
||||
<script src="../../js/png.bundle.js"></script>
|
||||
|
||||
<script type="application/javascript">
|
||||
document.oncontextmenu = function(e){
|
||||
return false;
|
||||
}
|
||||
|
||||
function newDelta(){
|
||||
return 50 * (Math.random() - 0.5)
|
||||
}
|
||||
|
||||
$(function () {
|
||||
$('[data-toggle="tooltip"]').tooltip()
|
||||
})
|
||||
|
||||
</script>
|
||||
<script type="application/javascript">
|
||||
var border = 20;
|
||||
var size = 512 + 2 * border; // 10 的边框
|
||||
//Create a Pixi Application
|
||||
var app = new PIXI.Application({width: size, height: size});
|
||||
//Add the canvas that Pixi automatically created for you to the HTML document
|
||||
document.getElementById("canvas").appendChild(app.view);
|
||||
|
||||
var bg = new PIXI.Container();
|
||||
bg.x = 0;
|
||||
bg.y = 0;
|
||||
app.stage.addChild(bg);
|
||||
|
||||
var rectangle = new PIXI.Graphics();
|
||||
rectangle.beginFill(0xFFFFFF);
|
||||
rectangle.drawRect(0, 0, app.renderer.view.width, app.renderer.view.height);
|
||||
rectangle.endFill();
|
||||
bg.addChild( rectangle )
|
||||
|
||||
var xyStyle = new PIXI.TextStyle({
|
||||
fontFamily: "Arial",
|
||||
fontSize: 18,
|
||||
fill: "blank"
|
||||
});
|
||||
|
||||
{
|
||||
// x 轴
|
||||
var lineX = new PIXI.Graphics();
|
||||
lineX.lineStyle(2, 0x000000, 1);
|
||||
lineX.moveTo( border, size /2);
|
||||
lineX.lineTo( size - border, size /2);
|
||||
bg.addChild(lineX);
|
||||
|
||||
// x 轴方向
|
||||
var triangle = new PIXI.Graphics();
|
||||
var baseX = size - border;
|
||||
var baseY = size /2;
|
||||
triangle.beginFill(0x000000);
|
||||
//Use `drawPolygon` to define the triangle as
|
||||
//a path array of x/y positions
|
||||
triangle.drawPolygon([
|
||||
baseX , baseY + 5, //First point
|
||||
baseX , baseY - 5, //Second point
|
||||
baseX + 8, baseY + 0 //Third point
|
||||
]);
|
||||
//Fill shape's color
|
||||
triangle.endFill();
|
||||
bg.addChild(triangle);
|
||||
|
||||
|
||||
var message = new PIXI.Text("紧急", xyStyle);
|
||||
message.position.set(baseX - 30 , baseY + 10 );
|
||||
bg.addChild(message);
|
||||
}
|
||||
|
||||
{
|
||||
// y 轴
|
||||
var lineX = new PIXI.Graphics();
|
||||
lineX.lineStyle(2, 0x000000, 1);
|
||||
lineX.moveTo( size /2, border );
|
||||
lineX.lineTo( size /2 , size - border);
|
||||
bg.addChild(lineX);
|
||||
|
||||
// x 轴方向
|
||||
var triangle = new PIXI.Graphics();
|
||||
var baseX = size / 2;
|
||||
var baseY = border;
|
||||
triangle.beginFill(0x000000);
|
||||
//Use `drawPolygon` to define the triangle as
|
||||
//a path array of x/y positions
|
||||
triangle.drawPolygon([
|
||||
baseX + 5, baseY , //First point
|
||||
baseX - 5, baseY , //Second point
|
||||
baseX, baseY - 8 //Third point
|
||||
]);
|
||||
//Fill shape's color
|
||||
triangle.endFill();
|
||||
bg.addChild(triangle);
|
||||
|
||||
var message = new PIXI.Text("重要", xyStyle);
|
||||
message.position.set(baseX - 40 , baseY );
|
||||
bg.addChild(message);
|
||||
}
|
||||
|
||||
var objStyle = new PIXI.TextStyle({
|
||||
fontFamily: "Arial",
|
||||
fontSize: 18,
|
||||
fill: 0x9966FF,
|
||||
|
||||
});
|
||||
|
||||
var objs = new PIXI.Container();
|
||||
app.stage.addChild(objs);
|
||||
|
||||
function newObj(x, y, name){
|
||||
|
||||
var obj = new PIXI.Container();
|
||||
obj.backgroundColor = 0x1099bb;
|
||||
obj.x = x;
|
||||
obj.y = y;
|
||||
objs.addChild(obj);
|
||||
|
||||
// point
|
||||
var circle = new PIXI.Graphics();
|
||||
circle.beginFill(0x9966FF);
|
||||
circle.drawCircle(0, 0, 5);
|
||||
circle.endFill();
|
||||
circle.position.set(0 , 0 );
|
||||
obj.addChild(circle);
|
||||
|
||||
var message = new PIXI.Text(name, objStyle);
|
||||
message.position.set( 8 , - 10);
|
||||
message.name = 'message'
|
||||
obj.addChild(message);
|
||||
|
||||
var input = new PIXI.TextInput({
|
||||
input: objStyle,
|
||||
box: {
|
||||
default: {fill: 0xE8E9F3, rounded: 12, stroke: {color: 0xCBCEE0, width: 3}},
|
||||
focused: {fill: 0xE1E3EE, rounded: 12, stroke: {color: 0xABAFC6, width: 3}},
|
||||
disabled: {fill: 0xDBDBDB, rounded: 12}
|
||||
}
|
||||
})
|
||||
input.position.set(0 + 8 , 0 - 10);
|
||||
input.placeholder = 'Enter your Text...'
|
||||
input.visible = false
|
||||
input.maxLength = 20
|
||||
input.on('keydown', function (keycode) {
|
||||
console.log('key pressed:', keycode)
|
||||
if ( 13 === keycode ) {
|
||||
endEdit()
|
||||
}
|
||||
})
|
||||
input.on('blur', function () {
|
||||
console.log( "blur" )
|
||||
endEdit()
|
||||
})
|
||||
function endEdit(){
|
||||
input.visible = false
|
||||
message.visible = true
|
||||
if ( input.text ) {
|
||||
message.text = input.text
|
||||
} else {
|
||||
app.stage.removeChild(obj);
|
||||
}
|
||||
}
|
||||
|
||||
obj.addChild(input);
|
||||
|
||||
// 实现头像拖动
|
||||
obj.interactive = true; //设置为可交互的
|
||||
|
||||
obj
|
||||
.on('touchstart', onDragStart)
|
||||
.on('touchend', onDragEnd)
|
||||
.on('touchmove', onDragMove)
|
||||
.on('mousedown', onDragStart )
|
||||
.on('mouseup', onDragEnd)
|
||||
.on('mouseupoutside', onDragEnd)
|
||||
.on('mousemove', onDragMove)
|
||||
.on("rightclick", function (event) {
|
||||
input.visible = true
|
||||
message.visible = false
|
||||
input.placeholder = "输入事件名称,回车确认,为空则删除整个事件。"
|
||||
input.text = message.text
|
||||
input.focus();
|
||||
})
|
||||
|
||||
|
||||
|
||||
function onDragStart(event) {
|
||||
this.data = event.data;
|
||||
this.alpha = 0.5;
|
||||
this.dragging = true;
|
||||
}
|
||||
|
||||
function onDragEnd() {
|
||||
this.alpha = 1;
|
||||
this.dragging = false;
|
||||
this.data = null;
|
||||
}
|
||||
|
||||
function onDragMove(event) {
|
||||
if (this.dragging) {
|
||||
this.position = this.data.getLocalPosition(this.parent);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
</script>
|
||||
|
||||
|
||||
<script type="application/javascript">
|
||||
|
||||
function addObj(){
|
||||
var x = size /4 + newDelta()
|
||||
var y = size /4 + newDelta()
|
||||
newObj(x, y, "新建事件")
|
||||
}
|
||||
|
||||
function clearObjs(){
|
||||
objs.removeChildren()
|
||||
}
|
||||
|
||||
function imports(){
|
||||
var oFlieImg = document.getElementById("custom-file-input");
|
||||
oFlieImg.onchange = function(e){
|
||||
var _self = e.currentTarget;
|
||||
var oSelfFile = _self.files[0]; //获取文件
|
||||
|
||||
// console.log(oSelfFile.name.lastIndexOf('.'));
|
||||
// 如果要限制文件类型的话这里可以判定oSelfFile.name‘.’最后一次出现的位置之后的单词是否为想要的类型
|
||||
// 或者判断oSelfFile.type
|
||||
// 判断文件大小为size单位为字节
|
||||
var oReader = new FileReader();
|
||||
oReader.readAsDataURL(oSelfFile); // 读取文件
|
||||
// 加载文件
|
||||
oReader.onload = function(ev){
|
||||
// 获取到FileReader读取文件的base64
|
||||
var oImgBase64 = ev.currentTarget.result;
|
||||
// console.log(oImgBase64)
|
||||
|
||||
var meta = png.de( oImgBase64 );
|
||||
try {
|
||||
var json = meta.crossnav
|
||||
json = JSON.parse( json )
|
||||
json.map(function (a){
|
||||
newObj(a.x, a.y, a.text)
|
||||
})
|
||||
|
||||
}catch ( e ) {
|
||||
alert("导入错误 " + e)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
oFlieImg.click();
|
||||
}
|
||||
|
||||
function outports(){
|
||||
var img = app.renderer.plugins.extract.base64(app.stage);
|
||||
let a = document.createElement("a"); // 生成一个a元素
|
||||
let event = new MouseEvent("click"); // 创建一个单击事件
|
||||
a.download = (new Date()).toLocaleString() + ".crossnav.png"
|
||||
|
||||
|
||||
let info = []
|
||||
for (let c of objs.children) {
|
||||
info.push({
|
||||
x : c.x,
|
||||
y : c.y,
|
||||
text : c.getChildByName('message').text
|
||||
})
|
||||
}
|
||||
|
||||
img = png.en( img, {
|
||||
"crossnav" : JSON.stringify( info )
|
||||
})
|
||||
|
||||
a.href = img; // 将生成的URL设置为a.href属性
|
||||
a.dispatchEvent(event); // 触发a的单击事件
|
||||
}
|
||||
|
||||
</script>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
Vendored
+2
File diff suppressed because one or more lines are too long
@@ -0,0 +1,72 @@
|
||||
{
|
||||
"glyphs": {
|
||||
"\"": {
|
||||
"ha": 694,
|
||||
"x_min": 174,
|
||||
"x_max": 521,
|
||||
"o": "m 304 982 q 282 841 288 911 l 271 700 l 190 700 l 184 873 q 174 982 179 928 l 304 982 m 521 982 q 499 841 505 911 l 488 700 l 407 700 l 401 873 q 391 982 396 928 l 521 982 z "
|
||||
},
|
||||
"M": {
|
||||
"ha": 694,
|
||||
"x_min": 49,
|
||||
"x_max": 635,
|
||||
"o": "m 635 27 l 526 27 l 526 689 l 515 689 l 385 27 l 298 27 l 168 689 l 157 689 l 157 27 l 49 27 l 49 955 l 217 955 l 336 342 l 347 342 l 467 955 l 635 955 l 635 27 z "
|
||||
},
|
||||
"d": {
|
||||
"ha": 694,
|
||||
"x_min": 49,
|
||||
"x_max": 597,
|
||||
"o": "m 597 27 l 488 27 l 488 109 q 412 38 456 60 q 309 16 369 16 q 125 95 201 16 q 49 331 49 174 q 125 570 49 488 q 309 651 201 651 q 412 627 369 651 q 488 553 456 602 l 488 955 l 597 955 l 597 27 m 488 331 q 442 494 488 434 q 331 553 396 553 q 209 494 250 553 q 168 331 168 434 q 209 171 168 228 q 331 114 250 114 q 442 171 396 114 q 488 331 488 228 z "
|
||||
},
|
||||
"r": {
|
||||
"ha": 694,
|
||||
"x_min": 141,
|
||||
"x_max": 543,
|
||||
"o": "m 543 526 q 369 496 439 543 q 250 336 298 450 l 250 27 l 141 27 l 141 635 l 250 635 l 250 477 q 372 605 298 564 q 543 646 445 646 l 543 526 z "
|
||||
},
|
||||
"汪": {
|
||||
"ha": 1389,
|
||||
"x_min": 141,
|
||||
"x_max": 1313,
|
||||
"o": "m 830 781 q 863 719 873 738 q 846 564 852 700 q 958 589 906 575 q 1050 564 1009 602 q 1020 518 1090 526 q 846 494 949 510 l 841 228 q 982 241 906 233 q 1142 258 1058 250 q 1270 212 1226 266 q 1221 171 1313 157 q 1004 179 1128 184 q 743 155 879 174 q 534 122 608 136 q 415 146 461 109 q 418 184 369 184 q 543 193 467 184 q 776 222 618 201 l 776 483 q 640 472 684 472 q 572 496 602 472 q 581 524 543 521 q 776 553 618 526 l 776 646 q 760 770 776 711 q 578 776 629 754 q 567 806 526 798 q 727 838 608 814 q 939 887 846 863 q 1069 882 1031 911 q 1031 827 1107 852 q 830 781 955 803 m 412 494 q 347 315 391 418 q 279 133 304 212 q 244 14 255 54 q 187 73 233 -27 q 174 182 141 174 q 252 260 206 190 q 369 453 298 331 q 412 494 439 575 m 385 873 q 298 968 320 928 q 377 985 277 1009 q 464 890 477 960 q 385 873 450 819 m 222 564 q 152 659 163 629 q 201 678 141 689 q 290 637 260 667 q 304 553 320 608 q 222 564 288 499 z "
|
||||
},
|
||||
"狗": {
|
||||
"ha": 1389,
|
||||
"x_min": 81,
|
||||
"x_max": 1270,
|
||||
"o": "m 423 705 q 312 632 374 662 q 190 581 250 602 q 206 608 130 559 q 401 770 282 656 q 334 871 369 830 q 263 947 298 911 q 277 960 228 982 q 369 903 326 939 q 445 825 412 868 q 532 936 494 873 q 564 1039 570 998 q 586 1066 559 1080 q 648 1017 613 1053 q 662 960 684 982 q 589 879 640 939 q 483 754 537 819 q 526 461 521 624 q 518 182 532 298 q 461 5 505 65 q 399 0 418 -54 q 312 95 380 54 q 312 125 244 136 q 407 125 380 114 q 448 285 434 136 q 450 499 461 434 q 301 326 385 407 q 149 212 217 244 q 138 228 81 179 q 285 391 195 277 q 434 635 374 505 q 423 705 429 673 m 792 722 q 914 727 846 722 q 1036 746 982 732 q 1107 773 1090 760 q 1166 770 1123 787 q 1240 724 1210 754 q 1242 662 1270 694 q 1218 467 1215 629 q 1204 206 1221 304 q 1158 43 1188 109 q 1080 -57 1128 -22 q 1020 -33 1031 -92 q 958 90 1009 27 q 982 114 906 152 q 1080 103 1058 76 q 1120 220 1101 130 q 1142 496 1139 309 q 1101 694 1145 684 q 990 692 1058 705 q 871 670 922 678 q 776 694 819 662 q 643 605 700 629 q 656 646 586 581 q 803 846 727 711 q 863 1034 879 982 q 949 1036 846 1085 q 987 987 1009 1009 q 917 890 966 966 q 792 722 868 814 m 895 347 q 884 293 955 293 q 684 271 819 293 q 648 244 662 190 q 624 372 635 298 q 594 486 613 445 q 605 521 575 526 q 662 507 635 515 q 757 510 689 499 q 846 540 825 521 q 898 548 868 559 q 963 513 928 537 q 966 461 998 488 q 895 347 933 434 m 678 461 q 684 315 684 358 q 846 336 732 320 q 852 450 852 418 q 806 483 852 488 q 678 461 760 477 z "
|
||||
},
|
||||
"白": {
|
||||
"ha": 1389,
|
||||
"x_min": 250,
|
||||
"x_max": 1172,
|
||||
"o": "m 472 678 q 817 732 711 716 q 958 765 922 749 q 1047 760 993 781 q 1137 708 1101 738 q 1142 643 1172 678 q 1101 407 1112 608 q 1063 125 1090 206 q 998 -11 1036 43 q 947 -3 960 -65 q 895 136 933 60 q 608 119 694 125 q 429 114 521 114 q 388 35 412 -5 q 358 149 363 76 q 347 288 353 222 q 320 475 342 353 q 274 635 298 597 q 277 673 250 673 q 334 667 304 673 q 423 667 363 662 q 545 863 483 743 q 600 1034 608 982 q 684 1036 591 1085 q 724 952 770 982 q 627 860 678 922 q 472 678 575 798 m 407 418 q 570 442 483 423 q 719 477 656 461 q 814 456 781 494 q 670 396 846 418 q 412 385 494 374 q 429 157 423 250 q 684 176 559 163 q 846 190 808 190 q 922 157 884 190 q 982 220 960 125 q 1009 385 1004 315 q 1015 553 1015 456 q 982 673 1015 651 q 863 686 949 694 q 385 624 776 678 q 407 418 401 461 z "
|
||||
}
|
||||
},
|
||||
"familyName": "KaiTi",
|
||||
"ascender": 1194,
|
||||
"descender": -195,
|
||||
"underlinePosition": -119,
|
||||
"underlineThickness": 65,
|
||||
"boundingBox": {
|
||||
"yMin": -255,
|
||||
"xMin": -65,
|
||||
"yMax": 1194,
|
||||
"xMax": 1432
|
||||
},
|
||||
"resolution": 1000,
|
||||
"original_font_information": {
|
||||
"format": 0,
|
||||
"copyright": "© Beijing ZhongYi Electronics Co., 1995-2005, All rights reserved",
|
||||
"fontFamily": "KaiTi",
|
||||
"fontSubfamily": "Regular",
|
||||
"uniqueID": "KaiTi",
|
||||
"fullName": "KaiTi",
|
||||
"version": "Version 5.01",
|
||||
"postScriptName": "KaiTi",
|
||||
"trademark": "Trademark of Beijing ZhongYi Electronics Co., China",
|
||||
"licence": "Microsoft supplied font. You may use this font to create, display, and print content as permitted by the license terms or terms of use, of the Microsoft product, service, or content in which this font was included. You may only (i) embed this font in content as permitted by the embedding restrictions included in this font; and (ii) temporarily download this font to a printer or other output device to help print content. Any other use is prohibited."
|
||||
},
|
||||
"cssFontWeight": "normal",
|
||||
"cssFontStyle": "normal"
|
||||
}
|
||||
File diff suppressed because one or more lines are too long
@@ -0,0 +1,29 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="chrome=1">
|
||||
<title>Title</title>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
|
||||
|
||||
|
||||
</body>
|
||||
<script type="application/javascript" src="ht.js"></script>
|
||||
<script type="application/javascript">
|
||||
|
||||
function init(){
|
||||
dataModel = new ht.DataModel();
|
||||
g3d = new ht.graph3d.Graph3dView(dataModel);
|
||||
g3d.setGridVisible(true);
|
||||
|
||||
borderPane = new ht.widget.BorderPane();
|
||||
borderPane.addToDOM();
|
||||
}
|
||||
|
||||
</script>
|
||||
|
||||
|
||||
</html>
|
||||
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
@@ -0,0 +1,78 @@
|
||||
/**
|
||||
* @author alteredq / http://alteredqualia.com/
|
||||
* @author mr.doob / http://mrdoob.com/
|
||||
*/
|
||||
|
||||
var Detector = {
|
||||
|
||||
canvas: !! window.CanvasRenderingContext2D,
|
||||
webgl: ( function () {
|
||||
|
||||
try {
|
||||
|
||||
var canvas = document.createElement( 'canvas' ); return !! ( window.WebGLRenderingContext && ( canvas.getContext( 'webgl' ) || canvas.getContext( 'experimental-webgl' ) ) );
|
||||
|
||||
} catch ( e ) {
|
||||
|
||||
return false;
|
||||
|
||||
}
|
||||
|
||||
} )(),
|
||||
workers: !! window.Worker,
|
||||
fileapi: window.File && window.FileReader && window.FileList && window.Blob,
|
||||
|
||||
getWebGLErrorMessage: function () {
|
||||
|
||||
var element = document.createElement( 'div' );
|
||||
element.id = 'webgl-error-message';
|
||||
element.style.fontFamily = 'monospace';
|
||||
element.style.fontSize = '13px';
|
||||
element.style.fontWeight = 'normal';
|
||||
element.style.textAlign = 'center';
|
||||
element.style.background = '#fff';
|
||||
element.style.color = '#000';
|
||||
element.style.padding = '1.5em';
|
||||
element.style.width = '400px';
|
||||
element.style.margin = '5em auto 0';
|
||||
|
||||
if ( ! this.webgl ) {
|
||||
|
||||
element.innerHTML = window.WebGLRenderingContext ? [
|
||||
'Your graphics card does not seem to support <a href="http://khronos.org/webgl/wiki/Getting_a_WebGL_Implementation" style="color:#000">WebGL</a>.<br />',
|
||||
'Find out how to get it <a href="http://get.webgl.org/" style="color:#000">here</a>.'
|
||||
].join( '\n' ) : [
|
||||
'Your browser does not seem to support <a href="http://khronos.org/webgl/wiki/Getting_a_WebGL_Implementation" style="color:#000">WebGL</a>.<br/>',
|
||||
'Find out how to get it <a href="http://get.webgl.org/" style="color:#000">here</a>.'
|
||||
].join( '\n' );
|
||||
|
||||
}
|
||||
|
||||
return element;
|
||||
|
||||
},
|
||||
|
||||
addGetWebGLMessage: function ( parameters ) {
|
||||
|
||||
var parent, id, element;
|
||||
|
||||
parameters = parameters || {};
|
||||
|
||||
parent = parameters.parent !== undefined ? parameters.parent : document.body;
|
||||
id = parameters.id !== undefined ? parameters.id : 'oldie';
|
||||
|
||||
element = Detector.getWebGLErrorMessage();
|
||||
element.id = id;
|
||||
|
||||
parent.appendChild( element );
|
||||
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
// browserify support
|
||||
if ( typeof module === 'object' ) {
|
||||
|
||||
module.exports = Detector;
|
||||
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
Vendored
+14
File diff suppressed because one or more lines are too long
Vendored
+13
@@ -0,0 +1,13 @@
|
||||
// tween.js - http://github.com/sole/tween.js
|
||||
'use strict';var TWEEN=TWEEN||function(){var a=[];return{REVISION:"7",getAll:function(){return a},removeAll:function(){a=[]},add:function(c){a.push(c)},remove:function(c){c=a.indexOf(c);-1!==c&&a.splice(c,1)},update:function(c){if(0===a.length)return!1;for(var b=0,d=a.length,c=void 0!==c?c:Date.now();b<d;)a[b].update(c)?b++:(a.splice(b,1),d--);return!0}}}();
|
||||
TWEEN.Tween=function(a){var c={},b={},d=1E3,e=0,f=null,h=TWEEN.Easing.Linear.None,r=TWEEN.Interpolation.Linear,k=[],l=null,m=!1,n=null,p=null;this.to=function(a,c){null!==c&&(d=c);b=a;return this};this.start=function(d){TWEEN.add(this);m=!1;f=void 0!==d?d:Date.now();f+=e;for(var g in b)if(null!==a[g]){if(b[g]instanceof Array){if(0===b[g].length)continue;b[g]=[a[g]].concat(b[g])}c[g]=a[g]}return this};this.stop=function(){TWEEN.remove(this);return this};this.delay=function(a){e=a;return this};this.easing=
|
||||
function(a){h=a;return this};this.interpolation=function(a){r=a;return this};this.chain=function(){k=arguments;return this};this.onStart=function(a){l=a;return this};this.onUpdate=function(a){n=a;return this};this.onComplete=function(a){p=a;return this};this.update=function(e){if(e<f)return!0;!1===m&&(null!==l&&l.call(a),m=!0);var g=(e-f)/d,g=1<g?1:g,i=h(g),j;for(j in c){var s=c[j],q=b[j];a[j]=q instanceof Array?r(q,i):s+(q-s)*i}null!==n&&n.call(a,i);if(1==g){null!==p&&p.call(a);g=0;for(i=k.length;g<
|
||||
i;g++)k[g].start(e);return!1}return!0}};
|
||||
TWEEN.Easing={Linear:{None:function(a){return a}},Quadratic:{In:function(a){return a*a},Out:function(a){return a*(2-a)},InOut:function(a){return 1>(a*=2)?0.5*a*a:-0.5*(--a*(a-2)-1)}},Cubic:{In:function(a){return a*a*a},Out:function(a){return--a*a*a+1},InOut:function(a){return 1>(a*=2)?0.5*a*a*a:0.5*((a-=2)*a*a+2)}},Quartic:{In:function(a){return a*a*a*a},Out:function(a){return 1- --a*a*a*a},InOut:function(a){return 1>(a*=2)?0.5*a*a*a*a:-0.5*((a-=2)*a*a*a-2)}},Quintic:{In:function(a){return a*a*a*
|
||||
a*a},Out:function(a){return--a*a*a*a*a+1},InOut:function(a){return 1>(a*=2)?0.5*a*a*a*a*a:0.5*((a-=2)*a*a*a*a+2)}},Sinusoidal:{In:function(a){return 1-Math.cos(a*Math.PI/2)},Out:function(a){return Math.sin(a*Math.PI/2)},InOut:function(a){return 0.5*(1-Math.cos(Math.PI*a))}},Exponential:{In:function(a){return 0===a?0:Math.pow(1024,a-1)},Out:function(a){return 1===a?1:1-Math.pow(2,-10*a)},InOut:function(a){return 0===a?0:1===a?1:1>(a*=2)?0.5*Math.pow(1024,a-1):0.5*(-Math.pow(2,-10*(a-1))+2)}},Circular:{In:function(a){return 1-
|
||||
Math.sqrt(1-a*a)},Out:function(a){return Math.sqrt(1- --a*a)},InOut:function(a){return 1>(a*=2)?-0.5*(Math.sqrt(1-a*a)-1):0.5*(Math.sqrt(1-(a-=2)*a)+1)}},Elastic:{In:function(a){var c,b=0.1;if(0===a)return 0;if(1===a)return 1;!b||1>b?(b=1,c=0.1):c=0.4*Math.asin(1/b)/(2*Math.PI);return-(b*Math.pow(2,10*(a-=1))*Math.sin((a-c)*2*Math.PI/0.4))},Out:function(a){var c,b=0.1;if(0===a)return 0;if(1===a)return 1;!b||1>b?(b=1,c=0.1):c=0.4*Math.asin(1/b)/(2*Math.PI);return b*Math.pow(2,-10*a)*Math.sin((a-c)*
|
||||
2*Math.PI/0.4)+1},InOut:function(a){var c,b=0.1;if(0===a)return 0;if(1===a)return 1;!b||1>b?(b=1,c=0.1):c=0.4*Math.asin(1/b)/(2*Math.PI);return 1>(a*=2)?-0.5*b*Math.pow(2,10*(a-=1))*Math.sin((a-c)*2*Math.PI/0.4):0.5*b*Math.pow(2,-10*(a-=1))*Math.sin((a-c)*2*Math.PI/0.4)+1}},Back:{In:function(a){return a*a*(2.70158*a-1.70158)},Out:function(a){return--a*a*(2.70158*a+1.70158)+1},InOut:function(a){return 1>(a*=2)?0.5*a*a*(3.5949095*a-2.5949095):0.5*((a-=2)*a*(3.5949095*a+2.5949095)+2)}},Bounce:{In:function(a){return 1-
|
||||
TWEEN.Easing.Bounce.Out(1-a)},Out:function(a){return a<1/2.75?7.5625*a*a:a<2/2.75?7.5625*(a-=1.5/2.75)*a+0.75:a<2.5/2.75?7.5625*(a-=2.25/2.75)*a+0.9375:7.5625*(a-=2.625/2.75)*a+0.984375},InOut:function(a){return 0.5>a?0.5*TWEEN.Easing.Bounce.In(2*a):0.5*TWEEN.Easing.Bounce.Out(2*a-1)+0.5}}};
|
||||
TWEEN.Interpolation={Linear:function(a,c){var b=a.length-1,d=b*c,e=Math.floor(d),f=TWEEN.Interpolation.Utils.Linear;return 0>c?f(a[0],a[1],d):1<c?f(a[b],a[b-1],b-d):f(a[e],a[e+1>b?b:e+1],d-e)},Bezier:function(a,c){var b=0,d=a.length-1,e=Math.pow,f=TWEEN.Interpolation.Utils.Bernstein,h;for(h=0;h<=d;h++)b+=e(1-c,d-h)*e(c,h)*a[h]*f(d,h);return b},CatmullRom:function(a,c){var b=a.length-1,d=b*c,e=Math.floor(d),f=TWEEN.Interpolation.Utils.CatmullRom;return a[0]===a[b]?(0>c&&(e=Math.floor(d=b*(1+c))),f(a[(e-
|
||||
1+b)%b],a[e],a[(e+1)%b],a[(e+2)%b],d-e)):0>c?a[0]-(f(a[0],a[0],a[1],a[1],-d)-a[0]):1<c?a[b]-(f(a[b],a[b],a[b-1],a[b-1],d-b)-a[b]):f(a[e?e-1:0],a[e],a[b<e+1?b:e+1],a[b<e+2?b:e+2],d-e)},Utils:{Linear:function(a,c,b){return(c-a)*b+a},Bernstein:function(a,c){var b=TWEEN.Interpolation.Utils.Factorial;return b(a)/b(c)/b(a-c)},Factorial:function(){var a=[1];return function(c){var b=1,d;if(a[c])return a[c];for(d=c;1<d;d--)b*=d;return a[c]=b}}(),CatmullRom:function(a,c,b,d,e){var a=0.5*(b-a),d=0.5*(d-c),f=
|
||||
e*e;return(2*c-2*b+a+d)*e*f+(-3*c+3*b-2*a-d)*f+a*e+c}}};
|
||||
@@ -0,0 +1,441 @@
|
||||
// ----- setup ----- //
|
||||
|
||||
var illoElem = document.querySelector('.illo');
|
||||
var sceneSize = 96;
|
||||
var TAU = Zdog.TAU;
|
||||
var ROOT3 = Math.sqrt(3);
|
||||
var ROOT5 = Math.sqrt(5);
|
||||
var PHI = ( 1 + ROOT5 ) / 2;
|
||||
var isSpinning = true;
|
||||
var viewRotation = new Zdog.Vector();
|
||||
var displaySize;
|
||||
|
||||
// colors
|
||||
var eggplant = '#636';
|
||||
var garnet = '#C25';
|
||||
var orange = '#E62';
|
||||
var gold = '#EA0';
|
||||
var yellow = '#ED0';
|
||||
|
||||
var illo = new Zdog.Illustration({
|
||||
element: illoElem,
|
||||
scale: 8,
|
||||
resize: 'fullscreen',
|
||||
onResize: function( width, height ) {
|
||||
displaySize = Math.min( width, height );
|
||||
this.zoom = Math.floor( displaySize / sceneSize );
|
||||
},
|
||||
});
|
||||
|
||||
var solids = [];
|
||||
|
||||
// ----- hourglass ----- //
|
||||
|
||||
( function() {
|
||||
|
||||
var hourglass = new Zdog.Anchor({
|
||||
addTo: illo,
|
||||
translate: { x: 0, y: -4 },
|
||||
});
|
||||
|
||||
solids.push( hourglass );
|
||||
|
||||
var hemi = new Zdog.Hemisphere({
|
||||
diameter: 2,
|
||||
translate: { z: -1 },
|
||||
addTo: hourglass,
|
||||
color: garnet,
|
||||
backface: orange,
|
||||
stroke: false,
|
||||
});
|
||||
|
||||
hemi.copy({
|
||||
translate: { z: 1 },
|
||||
rotate: { y: TAU/2 },
|
||||
color: eggplant,
|
||||
backface: gold,
|
||||
});
|
||||
|
||||
})();
|
||||
|
||||
// ----- sphere ----- //
|
||||
|
||||
( function() {
|
||||
|
||||
var sphere = new Zdog.Anchor({
|
||||
addTo: illo,
|
||||
translate: { x: -4, y: -4 },
|
||||
});
|
||||
|
||||
solids.push( sphere );
|
||||
|
||||
var hemi = new Zdog.Hemisphere({
|
||||
diameter: 2,
|
||||
addTo: sphere,
|
||||
color: orange,
|
||||
backface: eggplant,
|
||||
stroke: false,
|
||||
});
|
||||
|
||||
hemi.copy({
|
||||
rotate: { y: TAU/2 },
|
||||
color: eggplant,
|
||||
backface: orange,
|
||||
});
|
||||
|
||||
})();
|
||||
|
||||
// ----- cylinder ----- //
|
||||
|
||||
var cylinder = new Zdog.Cylinder({
|
||||
diameter: 2,
|
||||
length: 2,
|
||||
addTo: illo,
|
||||
translate: { x: 4, y: -4 },
|
||||
// rotate: { x: TAU/4 },
|
||||
color: gold,
|
||||
backface: garnet,
|
||||
stroke: false,
|
||||
});
|
||||
|
||||
solids.push( cylinder );
|
||||
|
||||
// ----- cone ----- //
|
||||
|
||||
var cone = new Zdog.Anchor({
|
||||
addTo: illo,
|
||||
translate: { x: -4, y: 0 },
|
||||
});
|
||||
|
||||
solids.push( cone );
|
||||
|
||||
new Zdog.Cone({
|
||||
diameter: 2,
|
||||
length: 2,
|
||||
addTo: cone,
|
||||
translate: { z: 1 },
|
||||
rotate: { y: TAU/2 },
|
||||
color: garnet,
|
||||
backface: gold,
|
||||
stroke: false,
|
||||
});
|
||||
|
||||
// ----- tetrahedron ----- //
|
||||
|
||||
( function() {
|
||||
|
||||
var tetrahedron = new Zdog.Anchor({
|
||||
addTo: illo,
|
||||
translate: { x: 0, y: 0 },
|
||||
scale: 2.5,
|
||||
});
|
||||
|
||||
var radius = 0.5;
|
||||
var inradius = Math.cos( TAU/6 ) * radius;
|
||||
var height = radius + inradius;
|
||||
|
||||
solids.push( tetrahedron );
|
||||
|
||||
var triangle = new Zdog.Polygon({
|
||||
sides: 3,
|
||||
radius: radius,
|
||||
addTo: tetrahedron,
|
||||
translate: { y: height/2 },
|
||||
fill: true,
|
||||
stroke: false,
|
||||
color: eggplant,
|
||||
// backface: false,
|
||||
});
|
||||
|
||||
|
||||
for ( var i=0; i < 3; i++ ) {
|
||||
var rotor1 = new Zdog.Anchor({
|
||||
addTo: tetrahedron,
|
||||
rotate: { y: TAU/3 * -i },
|
||||
});
|
||||
var rotor2 = new Zdog.Anchor({
|
||||
addTo: rotor1,
|
||||
translate: { z: inradius, y: height/2 },
|
||||
rotate: { x: Math.acos(1/3) * -1 + TAU/4 },
|
||||
});
|
||||
triangle.copy({
|
||||
addTo: rotor2,
|
||||
translate: { y: -inradius },
|
||||
color: [ gold, garnet, orange ][i],
|
||||
});
|
||||
}
|
||||
|
||||
triangle.rotate.set({ x: -TAU/4, z: -TAU/2 });
|
||||
|
||||
})();
|
||||
|
||||
// ----- octahedron ----- //
|
||||
|
||||
( function() {
|
||||
|
||||
var octahedron = new Zdog.Anchor({
|
||||
addTo: newcanvas,
|
||||
translate: { x: -4, y: 4 },
|
||||
scale: 1.75,
|
||||
});
|
||||
|
||||
var colorWheel = [ eggplant, garnet, orange, gold, yellow ];
|
||||
|
||||
// radius of triangle with side length = 1
|
||||
var radius = ROOT3/2 * 2/3;
|
||||
var height = radius * 3/2;
|
||||
var tilt = Math.asin( 0.5 / height );
|
||||
|
||||
[ -1, 1 ].forEach( function( ySide ) {
|
||||
for ( var i=0; i < 4; i++ ) {
|
||||
var rotor = new Zdog.Anchor({
|
||||
addTo: octahedron,
|
||||
rotate: { y: TAU/4 * (i + 1.5) * -1 },
|
||||
});
|
||||
|
||||
var anchor = new Zdog.Anchor({
|
||||
addTo: rotor,
|
||||
translate: { z: 0.5 },
|
||||
rotate: { x: tilt * ySide },
|
||||
// scale: { y: -ySide },
|
||||
});
|
||||
|
||||
new Zdog.Polygon({
|
||||
sides: 3,
|
||||
radius: radius,
|
||||
addTo: anchor,
|
||||
translate: { y: -radius/2 * ySide },
|
||||
scale: { y: ySide },
|
||||
stroke: false,
|
||||
fill: true,
|
||||
color: colorWheel[ i + 0.5 + 0.5*ySide ],
|
||||
backface: false,
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
})();
|
||||
|
||||
// ----- cube ----- //
|
||||
|
||||
var cube = new Zdog.Box({
|
||||
addTo: illo,
|
||||
width: 2,
|
||||
height: 2,
|
||||
depth: 2,
|
||||
translate: { x: 4, y: 0 },
|
||||
topFace: yellow,
|
||||
frontFace: gold,
|
||||
leftFace: orange,
|
||||
rightFace: orange,
|
||||
rearFace: garnet,
|
||||
bottomFace: eggplant,
|
||||
stroke: false,
|
||||
});
|
||||
|
||||
solids.push( cube );
|
||||
|
||||
// ----- dodecahedron ----- //
|
||||
|
||||
( function() {
|
||||
|
||||
var dodecahedron = new Zdog.Anchor({
|
||||
addTo: illo,
|
||||
translate: { x: 0, y: 4 },
|
||||
scale: 0.75,
|
||||
});
|
||||
|
||||
solids.push( dodecahedron );
|
||||
|
||||
// https://en.wikipedia.org/wiki/Regular_dodecahedron#Dimensions
|
||||
var midradius = ( PHI * PHI ) / 2;
|
||||
|
||||
// top & bottom faces
|
||||
var face = new Zdog.Polygon({
|
||||
sides: 5,
|
||||
radius: 1,
|
||||
addTo: dodecahedron,
|
||||
translate: { y: -midradius },
|
||||
rotate: { x: TAU/4 },
|
||||
fill: true,
|
||||
stroke: false,
|
||||
color: yellow,
|
||||
// backface: false,
|
||||
});
|
||||
|
||||
face.copy({
|
||||
translate: { y: midradius },
|
||||
rotate: { x: -TAU/4 },
|
||||
color: eggplant,
|
||||
});
|
||||
|
||||
|
||||
[ -1, 1 ].forEach( function( ySide ) {
|
||||
|
||||
|
||||
var colorWheel = {
|
||||
'-1': [ eggplant, garnet, gold, orange, garnet ],
|
||||
1: [ yellow, gold, garnet, orange, gold ],
|
||||
}[ ySide ];
|
||||
|
||||
for ( var i=0; i < 5; i++ ) {
|
||||
var rotor1 = new Zdog.Anchor({
|
||||
addTo: dodecahedron,
|
||||
rotate: { y: TAU/5 * (i) },
|
||||
});
|
||||
var rotor2 = new Zdog.Anchor({
|
||||
addTo: rotor1,
|
||||
rotate: { x: TAU/4*ySide - Math.atan(2) },
|
||||
});
|
||||
|
||||
face.copy({
|
||||
addTo: rotor2,
|
||||
translate: { z: midradius },
|
||||
rotate: { z: TAU/2 },
|
||||
color: colorWheel[i],
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
})();
|
||||
|
||||
// ----- isocahedron ----- //
|
||||
|
||||
( function() {
|
||||
|
||||
var isocahedron = new Zdog.Anchor({
|
||||
addTo: illo,
|
||||
translate: { x: 4, y: 4 },
|
||||
scale: 1.2,
|
||||
});
|
||||
|
||||
solids.push( isocahedron );
|
||||
|
||||
// geometry
|
||||
// radius of triangle with side length = 1
|
||||
var faceRadius = ROOT3/2 * 2/3;
|
||||
var faceHeight = faceRadius * 3/2;
|
||||
var capApothem = 0.5 / Math.tan( TAU/10 );
|
||||
var capRadius = 0.5 / Math.sin( TAU/10 );
|
||||
var capTilt = Math.asin( capApothem / faceHeight );
|
||||
var capSagitta = capRadius - capApothem;
|
||||
var sideTilt = Math.asin( capSagitta / faceHeight );
|
||||
var sideHeight = Math.sqrt( faceHeight*faceHeight - capSagitta*capSagitta );
|
||||
|
||||
// var colorWheel = [ eggplant, garnet, orange, gold, yellow ];
|
||||
|
||||
[ -1, 1 ].forEach( function( ySide ) {
|
||||
var capColors = {
|
||||
'-1': [ garnet, gold, yellow, gold, orange ],
|
||||
1: [ gold, garnet, eggplant, garnet, orange ],
|
||||
}[ ySide ];
|
||||
|
||||
var sideColors = {
|
||||
'-1': [ garnet, gold, yellow, orange, garnet ],
|
||||
1: [ gold, garnet, eggplant, orange, orange ],
|
||||
}[ ySide ];
|
||||
|
||||
for ( var i=0; i < 5; i++ ) {
|
||||
var rotor = new Zdog.Anchor({
|
||||
addTo: isocahedron,
|
||||
rotate: { y: TAU/5 * -i },
|
||||
translate: { y: sideHeight/2 * ySide },
|
||||
});
|
||||
|
||||
var capRotateX = -capTilt;
|
||||
var isYPos = ySide > 0;
|
||||
capRotateX += isYPos ? TAU/2 : 0;
|
||||
|
||||
var capAnchor = new Zdog.Anchor({
|
||||
addTo: rotor,
|
||||
translate: { z: capApothem * ySide },
|
||||
rotate: { x: capRotateX },
|
||||
});
|
||||
|
||||
// cap face
|
||||
var face = new Zdog.Polygon({
|
||||
sides: 3,
|
||||
radius: faceRadius,
|
||||
addTo: capAnchor,
|
||||
translate: { y: -faceRadius/2 },
|
||||
stroke: false,
|
||||
fill: true,
|
||||
color: capColors[i],
|
||||
// backface: false,
|
||||
});
|
||||
|
||||
var sideRotateX = -sideTilt;
|
||||
sideRotateX += isYPos ? 0 : TAU/2;
|
||||
var sideAnchor = capAnchor.copy({
|
||||
rotate: { x: sideRotateX },
|
||||
});
|
||||
|
||||
face.copy({
|
||||
addTo: sideAnchor,
|
||||
translate: { y: -faceRadius/2 },
|
||||
rotate: { y: TAU/2 },
|
||||
color: sideColors[i]
|
||||
});
|
||||
|
||||
}
|
||||
});
|
||||
|
||||
})();
|
||||
|
||||
// -- animate --- //
|
||||
|
||||
var keyframes = [
|
||||
{ x: 0, y: 0 },
|
||||
{ x: 0, y: TAU },
|
||||
{ x: TAU, y: TAU },
|
||||
];
|
||||
|
||||
var ticker = 0;
|
||||
var cycleCount = 180;
|
||||
var turnLimit = keyframes.length - 1;
|
||||
|
||||
function animate() {
|
||||
update();
|
||||
illo.renderGraph();
|
||||
requestAnimationFrame( animate );
|
||||
}
|
||||
|
||||
animate();
|
||||
|
||||
function update() {
|
||||
|
||||
if ( isSpinning ) {
|
||||
var progress = ticker / cycleCount;
|
||||
var tween = Zdog.easeInOut( progress % 1, 4 );
|
||||
var turn = Math.floor( progress % turnLimit );
|
||||
var keyA = keyframes[ turn ];
|
||||
var keyB = keyframes[ turn + 1 ];
|
||||
viewRotation.x = Zdog.lerp( keyA.x, keyB.x, tween );
|
||||
viewRotation.y = Zdog.lerp( keyA.y, keyB.y, tween );
|
||||
ticker++;
|
||||
}
|
||||
|
||||
solids.forEach( function( solid ) {
|
||||
solid.rotate.set( viewRotation );
|
||||
});
|
||||
|
||||
illo.updateGraph();
|
||||
}
|
||||
|
||||
// ----- inputs ----- //
|
||||
|
||||
var dragStartRX, dragStartRY;
|
||||
|
||||
new Zdog.Dragger({
|
||||
startElement: illoElem,
|
||||
onDragStart: function() {
|
||||
isSpinning = false;
|
||||
dragStartRX = viewRotation.x;
|
||||
dragStartRY = viewRotation.y;
|
||||
},
|
||||
onDragMove: function( pointer, moveX, moveY ) {
|
||||
viewRotation.x = dragStartRX - ( moveY / displaySize * TAU );
|
||||
viewRotation.y = dragStartRY - ( moveX / displaySize * TAU );
|
||||
},
|
||||
});
|
||||
Vendored
+6
@@ -0,0 +1,6 @@
|
||||
// stats.js - http://github.com/mrdoob/stats.js
|
||||
var Stats=function(){var l=Date.now(),m=l,g=0,n=Infinity,o=0,h=0,p=Infinity,q=0,r=0,s=0,f=document.createElement("div");f.id="stats";f.addEventListener("mousedown",function(b){b.preventDefault();t(++s%2)},!1);f.style.cssText="width:80px;opacity:0.9;cursor:pointer";var a=document.createElement("div");a.id="fps";a.style.cssText="padding:0 0 3px 3px;text-align:left;background-color:#002";f.appendChild(a);var i=document.createElement("div");i.id="fpsText";i.style.cssText="color:#0ff;font-family:Helvetica,Arial,sans-serif;font-size:9px;font-weight:bold;line-height:15px";
|
||||
i.innerHTML="FPS";a.appendChild(i);var c=document.createElement("div");c.id="fpsGraph";c.style.cssText="position:relative;width:74px;height:30px;background-color:#0ff";for(a.appendChild(c);74>c.children.length;){var j=document.createElement("span");j.style.cssText="width:1px;height:30px;float:left;background-color:#113";c.appendChild(j)}var d=document.createElement("div");d.id="ms";d.style.cssText="padding:0 0 3px 3px;text-align:left;background-color:#020;display:none";f.appendChild(d);var k=document.createElement("div");
|
||||
k.id="msText";k.style.cssText="color:#0f0;font-family:Helvetica,Arial,sans-serif;font-size:9px;font-weight:bold;line-height:15px";k.innerHTML="MS";d.appendChild(k);var e=document.createElement("div");e.id="msGraph";e.style.cssText="position:relative;width:74px;height:30px;background-color:#0f0";for(d.appendChild(e);74>e.children.length;)j=document.createElement("span"),j.style.cssText="width:1px;height:30px;float:left;background-color:#131",e.appendChild(j);var t=function(b){s=b;switch(s){case 0:a.style.display=
|
||||
"block";d.style.display="none";break;case 1:a.style.display="none",d.style.display="block"}};return{REVISION:11,domElement:f,setMode:t,begin:function(){l=Date.now()},end:function(){var b=Date.now();g=b-l;n=Math.min(n,g);o=Math.max(o,g);k.textContent=g+" MS ("+n+"-"+o+")";var a=Math.min(30,30-30*(g/200));e.appendChild(e.firstChild).style.height=a+"px";r++;b>m+1E3&&(h=Math.round(1E3*r/(b-m)),p=Math.min(p,h),q=Math.max(q,h),i.textContent=h+" FPS ("+p+"-"+q+")",a=Math.min(30,30-30*(h/100)),c.appendChild(c.firstChild).style.height=
|
||||
a+"px",m=b,r=0);return b},update:function(){l=this.end()}}};
|
||||
@@ -0,0 +1,379 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>Title</title>
|
||||
<style>
|
||||
|
||||
html, body {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
overflow: hidden;
|
||||
}
|
||||
/*canvas {*/
|
||||
/*width: 100%;*/
|
||||
/*height: 100%*/
|
||||
/*}*/
|
||||
</style>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
<script type="application/javascript" src="three.js"></script>
|
||||
<script type="application/javascript" src="stats.min.js"></script>
|
||||
<script>
|
||||
console.log( "document.body.clientWidth", document.body.clientWidth )
|
||||
console.log( "document.body.clientHeight", document.body.clientHeight)
|
||||
console.log( "document.body.offsetWidth", document.body.offsetWidth)
|
||||
console.log( "document.body.offsetHeight", document.body.offsetHeight)
|
||||
console.log( "document.body.scrollWidth", document.body.scrollWidth)
|
||||
console.log( "document.body.scrollHeight", document.body.scrollHeight)
|
||||
console.log( "document.body.scrollTop", document.body.scrollTop)
|
||||
console.log( "document.body.scrollLeft", document.body.scrollLeft)
|
||||
console.log( "window.screenTop", window.screenTop)
|
||||
console.log( "window.screenLeft", window.screenLeft)
|
||||
console.log( "window.screen.height", window.screen.height)
|
||||
console.log( "window.screen.width", window.screen.width)
|
||||
console.log( "window.screen.availHeight", window.screen.availHeight)
|
||||
console.log( "window.screen.availWidth", window.screen.availWidth)
|
||||
|
||||
|
||||
var mouseX = 0;
|
||||
var mouseY = 0;
|
||||
|
||||
var w = document.body.clientWidth
|
||||
var h = document.body.clientHeight
|
||||
|
||||
document.addEventListener('mousemove', onDocumentMouseMove, false );
|
||||
function onDocumentMouseMove( event ) {
|
||||
mouseX = ( event.clientX - w/2 );
|
||||
mouseY = ( event.clientY - h/2 );
|
||||
}
|
||||
|
||||
|
||||
var scene = new THREE.Scene();
|
||||
|
||||
|
||||
|
||||
var camera = new THREE.PerspectiveCamera(45, w / h , 0.1, 500);
|
||||
// var camera = new THREE.OrthographicCamera( w / -2, w /2, h/ 2, h/-2, 0.1, 500 );
|
||||
|
||||
var far = 50
|
||||
camera.position.x = 0;
|
||||
camera.position.y = - far / 2;
|
||||
camera.position.z = far;
|
||||
|
||||
// camera.up.set(1, 1, 1)
|
||||
camera.lookAt(new THREE.Vector3( 0, 0, 0 ));
|
||||
// console.log("scene.position)", scene.position)
|
||||
|
||||
var renderer = new THREE.WebGLRenderer({
|
||||
antialias:true
|
||||
});
|
||||
renderer.setSize(w, h);
|
||||
|
||||
|
||||
var stats = new Stats();
|
||||
stats.domElement.style.position = 'absolute';
|
||||
stats.domElement.style.left = '0px';
|
||||
stats.domElement.style.top = '0px';
|
||||
|
||||
document.body.appendChild(renderer.domElement);
|
||||
document.body.appendChild(stats.domElement);
|
||||
|
||||
{
|
||||
{
|
||||
var light = new THREE.AmbientLight(0xFFFFFF);
|
||||
light.position.set(100, 100, 200);
|
||||
scene.add(light);
|
||||
|
||||
}
|
||||
}
|
||||
// {
|
||||
// var light = new THREE.DirectionalLight(0xFFFFFF, 1.0, 0);
|
||||
// light.position.set(200, 100, 0);
|
||||
// scene.add(light);
|
||||
// }
|
||||
// {
|
||||
// var geometry = new THREE.CubeGeometry( 50, 50, 50, 4, 4);
|
||||
// // B start
|
||||
// var material = new THREE.MeshLambertMaterial( { color:0x880000} );
|
||||
// // B end
|
||||
// var mesh = new THREE.Mesh( geometry,material);
|
||||
// mesh.position = new THREE.Vector3(0,0,0);
|
||||
// scene.add(mesh);
|
||||
// }
|
||||
{
|
||||
// 网格的边长是1000,每个小网格的边长是50
|
||||
var helper = new THREE.GridHelper( 1000, 50 , 0x0000ff, 0x808080 );
|
||||
scene.add( helper );
|
||||
}
|
||||
var curMeth;
|
||||
{
|
||||
var geometry = new THREE.BoxGeometry( 1,1,1 );
|
||||
|
||||
for ( var i = 0; i < geometry.faces.length; i += 2 ) {
|
||||
|
||||
var hex = Math.random() * 0xffffff;
|
||||
geometry.faces[ i ].color.setHex( hex );
|
||||
geometry.faces[ i + 1 ].color.setHex( hex );
|
||||
|
||||
}
|
||||
|
||||
var material = new THREE.LineBasicMaterial( { vertexColors: THREE.FaceColors} );
|
||||
var mesh = new THREE.Mesh( geometry,material);
|
||||
mesh.position = new THREE.Vector3(0, -10 ,0);
|
||||
scene.add(mesh);
|
||||
curMeth = mesh
|
||||
}
|
||||
|
||||
var watting;
|
||||
{
|
||||
var loader = new THREE.FontLoader();
|
||||
//导入字体,设定字体,这里的话,你们找对自己的字体路径,可能和我的不一样的!!下载的three.js包里面examples/fonts里面有字体
|
||||
loader.load('./helvetiker_bold.typeface.json', function(font) {
|
||||
|
||||
// 文字
|
||||
var text = "Watting...";
|
||||
|
||||
|
||||
var g = new THREE.TextGeometry(text, {
|
||||
// 设定文字字体,
|
||||
font: font,
|
||||
//尺寸
|
||||
size: 20,
|
||||
//厚度
|
||||
height: 5,
|
||||
});
|
||||
//计算边界,暂时不用管
|
||||
g.computeBoundingBox();
|
||||
|
||||
|
||||
{
|
||||
g = new THREE.EdgesGeometry(g); //或WireframeGeometry(几何)
|
||||
|
||||
var mat = new THREE.LineBasicMaterial({color : 0xffffff, linewidth : 2});
|
||||
|
||||
var wireframe = new THREE.LineSegments( g , mat );
|
||||
|
||||
scene.add(wireframe);
|
||||
watting = wireframe
|
||||
}
|
||||
|
||||
|
||||
// //3D文字材质
|
||||
// var m = new THREE.LineBasicMaterial({color: 0xffff00});
|
||||
// var mesh = new THREE.Mesh(g, m);
|
||||
// mesh.position = new THREE.Vector3(0, -100, 0);
|
||||
//
|
||||
// // 加入到场景中
|
||||
// scene.add(mesh);
|
||||
|
||||
})
|
||||
}
|
||||
|
||||
{
|
||||
var loader = new THREE.FontLoader();
|
||||
//导入字体,设定字体,这里的话,你们找对自己的字体路径,可能和我的不一样的!!下载的three.js包里面examples/fonts里面有字体
|
||||
loader.load('./yahei.json', function(font){
|
||||
|
||||
{
|
||||
var xMid;
|
||||
|
||||
var color = 0x006699;
|
||||
|
||||
var matDark = new THREE.LineBasicMaterial( {
|
||||
color: color,
|
||||
side: THREE.DoubleSide
|
||||
} );
|
||||
|
||||
var matLite = new THREE.MeshBasicMaterial( {
|
||||
color: color,
|
||||
transparent: true,
|
||||
opacity: 0.4,
|
||||
side: THREE.DoubleSide
|
||||
} );
|
||||
|
||||
var message = "亿企云平台";
|
||||
|
||||
var shapes = font.generateShapes( message, 10 );
|
||||
|
||||
var geometry = new THREE.ShapeBufferGeometry( shapes );
|
||||
|
||||
geometry.computeBoundingBox();
|
||||
|
||||
xMid = - 0.5 * ( geometry.boundingBox.max.x - geometry.boundingBox.min.x );
|
||||
|
||||
geometry.translate( xMid, 0, 0 );
|
||||
|
||||
// make shape ( N.B. edge view not visible )
|
||||
|
||||
text = new THREE.Mesh( geometry, matLite );
|
||||
text.position.z = - 10;
|
||||
scene.add( text );
|
||||
|
||||
// make line shape ( N.B. edge view remains visible )
|
||||
|
||||
var holeShapes = [];
|
||||
|
||||
for ( var i = 0; i < shapes.length; i ++ ) {
|
||||
|
||||
var shape = shapes[ i ];
|
||||
|
||||
if ( shape.holes && shape.holes.length > 0 ) {
|
||||
|
||||
for ( var j = 0; j < shape.holes.length; j ++ ) {
|
||||
|
||||
var hole = shape.holes[ j ];
|
||||
holeShapes.push( hole );
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
shapes.push.apply( shapes, holeShapes );
|
||||
|
||||
var lineText = new THREE.Object3D();
|
||||
|
||||
for ( var i = 0; i < shapes.length; i ++ ) {
|
||||
|
||||
var shape = shapes[ i ];
|
||||
|
||||
var points = shape.getPoints();
|
||||
var geometry = new THREE.BufferGeometry().setFromPoints( points );
|
||||
|
||||
geometry.translate( xMid, 0, 0 );
|
||||
|
||||
var lineMesh = new THREE.Line( geometry, matDark );
|
||||
lineText.add( lineMesh );
|
||||
|
||||
}
|
||||
|
||||
scene.add( lineText );
|
||||
}
|
||||
|
||||
|
||||
if ( watting ){
|
||||
setTimeout(function () {
|
||||
scene.remove( watting )
|
||||
}, 10000 )
|
||||
|
||||
}
|
||||
|
||||
});
|
||||
}
|
||||
|
||||
// {
|
||||
// var geometry = new THREE.CylinderGeometry( 5,5,5);
|
||||
// var material = new THREE.MeshLambertMaterial( { color:0xFFFFFF} );
|
||||
// var mesh = new THREE.Mesh( geometry,material);
|
||||
// mesh.position = new THREE.Vector3(0,0,0);
|
||||
// scene.add(mesh);
|
||||
// }
|
||||
// {
|
||||
// var axisHelper =new THREE.AxisHelper(20);
|
||||
// scene.add(axisHelper);
|
||||
//
|
||||
// }
|
||||
// {
|
||||
//
|
||||
//
|
||||
//
|
||||
// var material = new THREE.LineBasicMaterial( { vertexColors: true } );
|
||||
// var color0 = new THREE.Color( 0x444444 );
|
||||
// var color1 = new THREE.Color( 0xFF0000 );
|
||||
// var color2 = new THREE.Color( 0x00FF00 );
|
||||
// var color3 = new THREE.Color( 0x0000FF );
|
||||
//
|
||||
//
|
||||
// // 线的材质可以由2点的颜色决定
|
||||
// var p0 = new THREE.Vector3( 0, 0, 0 );
|
||||
// var p1 = new THREE.Vector3( 100, 0, 0 );
|
||||
// var p2 = new THREE.Vector3( 0, 100, 0 );
|
||||
// var p3 = new THREE.Vector3( 0, 0, 100 );
|
||||
// var geometry1 = new THREE.Geometry();
|
||||
// geometry1.vertices.push(p0);
|
||||
// geometry1.vertices.push(p1);
|
||||
// geometry1.colors.push( color0, color1 );
|
||||
//
|
||||
// var geometry2 = new THREE.Geometry();
|
||||
// geometry2.vertices.push(p0);
|
||||
// geometry2.vertices.push(p2);
|
||||
// geometry2.colors.push( color0, color2 );
|
||||
// // geometry.vertices.push(p3);
|
||||
//
|
||||
// var geometry3 = new THREE.Geometry();
|
||||
// geometry3.vertices.push(p0);
|
||||
// geometry3.vertices.push(p3);
|
||||
// geometry3.colors.push( color0, color3 );
|
||||
//
|
||||
// var line1 = new THREE.Line( geometry1, material, THREE.LineSegments );
|
||||
// var line2 = new THREE.Line( geometry2, material, THREE.LineSegments );
|
||||
// var line3 = new THREE.Line( geometry3, material, THREE.LineSegments );
|
||||
//
|
||||
// scene.add(line1);
|
||||
// scene.add(line2);
|
||||
// scene.add(line3);
|
||||
// }
|
||||
|
||||
function render() {
|
||||
requestAnimationFrame(render);
|
||||
renderer.render(scene, camera);
|
||||
}
|
||||
|
||||
function round(a, b, r, angle) {
|
||||
var na = r * Math.sin( angle )
|
||||
var nb = r * Math.cos( angle )
|
||||
return {
|
||||
na,nb
|
||||
}
|
||||
}
|
||||
var angle = 0
|
||||
var v = 0.01
|
||||
|
||||
setInterval(function () {
|
||||
|
||||
if ( v == 0.01 ){
|
||||
v = 0.1
|
||||
} else {
|
||||
v = 0.01
|
||||
}
|
||||
|
||||
}, 3000 )
|
||||
|
||||
function animate() {
|
||||
|
||||
// // curMeth.rotation.y += 0.01;
|
||||
// camera.position.x += ( mouseX - camera.position.x ) * 0.05;
|
||||
// camera.position.y += ( - mouseY - camera.position.y ) * 0.05;
|
||||
// // 相机永远指向场景的原点位置,场景的位置默认在世界坐标的原点,而且一般我们不会移动scene的位置
|
||||
// camera.lookAt( scene.position );
|
||||
|
||||
// camera.position.x = camera.position.x - 0.11;
|
||||
|
||||
angle += v
|
||||
var p = round(camera.position.x, camera.position.z, 50, angle)
|
||||
camera.position.x = p.na
|
||||
camera.position.z = p.nb
|
||||
camera.lookAt( scene.position )
|
||||
|
||||
|
||||
stats.update()
|
||||
render();
|
||||
|
||||
requestAnimationFrame( animate );
|
||||
|
||||
}
|
||||
|
||||
animate()
|
||||
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
+48034
File diff suppressed because one or more lines are too long
@@ -0,0 +1,519 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="full-screen" content="yes">
|
||||
<meta name="browsermode" content="application">
|
||||
<meta name="x5-orientation" content="portrait">
|
||||
<meta name="x5-fullscreen" content="true">
|
||||
<meta name="x5-page-mode" content="app">
|
||||
<meta name="viewport" content="width=device-width,initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=no,minimal-ui">
|
||||
<meta name="apple-mobile-web-app-capable" content="yes" />
|
||||
<meta name="apple-mobile-web-app-status-bar-style" content="black-translucent" />
|
||||
|
||||
<meta name="apple-mobile-web-app-title" content="应用标题">
|
||||
<meta content="telephone=no" name="format-detection" />
|
||||
<meta content="email=no" name="format-detection" />
|
||||
|
||||
|
||||
|
||||
<title>VR 亿企云平台</title>
|
||||
</head>
|
||||
<body onload="draw();">
|
||||
|
||||
|
||||
<div style="position: fixed;">
|
||||
<div id="moAccel"></div>
|
||||
<div id="moCalcTiltLR"></div>
|
||||
<div id="moCalcTiltFB"></div>
|
||||
<div id="imgLogo">-----------------</div>
|
||||
|
||||
<div id="arrow"></div>
|
||||
<div id="acceleration"></div>
|
||||
</div>
|
||||
|
||||
<script type="application/javascript">
|
||||
|
||||
(function () {
|
||||
var arrow = document.getElementById("arrow");
|
||||
try {
|
||||
var text = "";
|
||||
window.addEventListener("deviceorientation", orientationHandler, false);
|
||||
function orientationHandler(event) {
|
||||
text = ""
|
||||
|
||||
text += "左右旋转:rotate alpha{" + Math.round(event.alpha) + "deg)<br>";
|
||||
text += "前后旋转:rotate beta{" + Math.round(event.beta) + "deg)<br>";
|
||||
text += "扭转设备:rotate gamma{" + Math.round(event.gamma) + "deg)<br>";
|
||||
arrow.innerHTML = text;
|
||||
}
|
||||
}
|
||||
catch (e) {
|
||||
arrow.innerHTML = e.message
|
||||
}
|
||||
})()
|
||||
|
||||
</script>
|
||||
<script type="application/javascript">
|
||||
|
||||
var vx = vy = vz = 0; //用以获取xyz轴当前的数据
|
||||
var sx = sy = sz = 0;
|
||||
|
||||
var startTime = new Date().getTime(); // 最初的开始时间,单位:毫秒
|
||||
|
||||
function deviceMotionHandler2(eventData) {
|
||||
// 捕捉重力加速度
|
||||
var acceleration = eventData.accelerationIncludingGravity;
|
||||
// 打印加速数据
|
||||
var rawAcceleration = "[" + Math.round(acceleration.x) + ", " +Math.round(acceleration.y) + ", " + Math.round(acceleration.z) + "]";
|
||||
// Z轴,可知设备朝上或者朝下
|
||||
var facingUp = -1;
|
||||
if (acceleration.z > 0) {
|
||||
facingUp = +1;
|
||||
}
|
||||
// 根据重力通过 acceleration.x|y 转换得到加速值,
|
||||
// 运用重力加速度9.81来计算得到一个百分比然后乘以转换角度90
|
||||
var tiltLR = Math.round(((acceleration.x) / 9.81) * -90);
|
||||
var tiltFB = Math.round(((acceleration.y + 9.81) / 9.81) * 90 * facingUp);
|
||||
// 打印加速度的计算结果
|
||||
document.getElementById("moAccel").innerHTML = rawAcceleration;
|
||||
document.getElementById("moCalcTiltLR").innerHTML = tiltLR;
|
||||
document.getElementById("moCalcTiltFB").innerHTML = tiltFB;
|
||||
// 将2D和3D的转换应用到图片上
|
||||
var rotation = "rotate(" + tiltLR + "deg) (1,0,0, " + (tiltFB) + "deg)";
|
||||
document.getElementById("imgLogo").innerHTML = rotation;
|
||||
}
|
||||
|
||||
if (window.DeviceMotionEvent) {
|
||||
|
||||
window.addEventListener('devicemotion', function deviceMotionHandler(eventData){
|
||||
deviceMotionHandler2(eventData)
|
||||
|
||||
// document.getElementById("acceleration").innerText = "dz = " + eventData.acceleration.x.toFixed(2) + " " + eventData.accelerationIncludingGravity.x.toFixed(2)
|
||||
var currTime = new Date().getTime(); //当前时间
|
||||
|
||||
var diffTime = currTime - startTime;//当前时间减最初时间,得到当前时间差
|
||||
|
||||
|
||||
var acceleration = eventData.acceleration; //获得加速器对象
|
||||
|
||||
var x = acceleration.x
|
||||
var y = acceleration.y
|
||||
var z = acceleration.z
|
||||
vx += x; //获取x轴当前加速度
|
||||
|
||||
vy += y; //获取y轴当前加速度
|
||||
|
||||
vz += z; //获取z轴当前加速度
|
||||
|
||||
sx += diffTime * vx
|
||||
sy += diffTime * vy
|
||||
sz += diffTime * vz
|
||||
|
||||
|
||||
document.getElementById("acceleration").innerText = "\r\n" +
|
||||
"x = " + x.toFixed(2) + "\n" +
|
||||
"y = " + y.toFixed(2) + "\n" +
|
||||
"z = " + z.toFixed(2) + "\n" +
|
||||
"vx = " + vx.toFixed(2) + "\n" +
|
||||
"vy = " + vy.toFixed(2) + "\n" +
|
||||
"vz = " + vz.toFixed(2) + "\n" +
|
||||
"sx = " + sx.toFixed(2) + "\n" +
|
||||
"sy = " + sy.toFixed(2) + "\n" +
|
||||
"sz = " + sz.toFixed(2) + "\n" +
|
||||
"\n";
|
||||
|
||||
}, false);
|
||||
|
||||
}
|
||||
|
||||
</script>
|
||||
|
||||
<script src="./three.js"></script>
|
||||
<script src="./lib/OrbitControls.js"></script>
|
||||
<script src="./stats.min.js"></script>
|
||||
<script src="./lib/dat.gui.min.js"></script>
|
||||
<script src="./lib/Detector.js"></script>
|
||||
<script src="./lib/tween.min.js"></script>
|
||||
|
||||
|
||||
<script>
|
||||
var renderer, camera, scene, gui, light, stats, controls;
|
||||
//字体的点集
|
||||
var originParticleField,pointsMaterial,geo_ver,geo_ver2,tween,hearts=[];
|
||||
//初始点
|
||||
var baseLens =10000,basePoint=[],baseArea=160;
|
||||
for(var i=0;i<baseLens;i++){
|
||||
var x= Number(Math.random()*baseArea)-baseArea/2;
|
||||
var y= Number(Math.random()*baseArea)-baseArea/2;
|
||||
var z= Number(Math.random()*baseArea)-baseArea/2;
|
||||
var obj = {
|
||||
x:x,
|
||||
y:y,
|
||||
z:z
|
||||
}
|
||||
basePoint.push(obj);
|
||||
}
|
||||
|
||||
|
||||
|
||||
function initRender() {
|
||||
renderer = new THREE.WebGLRenderer({antialias: true});
|
||||
renderer.setPixelRatio(window.devicePixelRatio);
|
||||
renderer.setSize(window.innerWidth, window.innerHeight);
|
||||
renderer.setClearColor(0xeeeeee);
|
||||
renderer.shadowMap.enabled = true;
|
||||
//告诉渲染器需要阴影效果
|
||||
document.body.appendChild(renderer.domElement);
|
||||
}
|
||||
|
||||
function initCamera() {
|
||||
camera = new THREE.PerspectiveCamera(45, window.innerWidth / window.innerHeight, 0.1, 200);
|
||||
camera.position.set(0, 20, 80 );
|
||||
}
|
||||
|
||||
function initScene() {
|
||||
scene = new THREE.Scene();
|
||||
scene.background = new THREE.Color( 0xa0a0a0 );
|
||||
scene.fog = new THREE.Fog( 0xa0a0a0, 5, 250 );
|
||||
}
|
||||
|
||||
//初始化dat.GUI简化试验流程
|
||||
function initGui() {
|
||||
// //声明一个保存需求修改的相关数据的对象
|
||||
// gui = {
|
||||
// bump:0.03,
|
||||
// animation:false
|
||||
// };
|
||||
// var datGui = new dat.GUI();
|
||||
// //将设置属性添加到gui当中,gui.add(对象,属性,最小值,最大值)
|
||||
// datGui.add(gui, "bump", -1, 1).onChange(function (e) {
|
||||
// cube1.material.bumpScale = e;
|
||||
// });
|
||||
//
|
||||
// datGui.add(gui, "animation");
|
||||
}
|
||||
|
||||
function initLight() {
|
||||
scene.add(new THREE.AmbientLight(0x444444));
|
||||
|
||||
light = new THREE.DirectionalLight(0xffffff);
|
||||
light.position.set(0, 600, 240 );
|
||||
|
||||
light.castShadow = true;
|
||||
light.shadow.camera.top = 10;
|
||||
light.shadow.camera.bottom = -10;
|
||||
light.shadow.camera.left = -10;
|
||||
light.shadow.camera.right = 10;
|
||||
|
||||
//告诉平行光需要开启阴影投射
|
||||
light.castShadow = true;
|
||||
|
||||
// scene.add(light);
|
||||
}
|
||||
|
||||
function initModel() {
|
||||
|
||||
//辅助工具
|
||||
var helper = new THREE.AxesHelper(50);
|
||||
scene.add(helper);
|
||||
|
||||
// 地板
|
||||
var mesh = new THREE.Mesh( new THREE.PlaneBufferGeometry( 400, 400 ), new THREE.MeshPhongMaterial( { color: 0xffffff, depthWrite: false } ) );
|
||||
mesh.rotation.x = - Math.PI / 2;
|
||||
mesh.receiveShadow = true;
|
||||
scene.add( mesh );
|
||||
|
||||
//添加地板割线
|
||||
var grid = new THREE.GridHelper( 400, 50, 0x000000, 0x000000 );
|
||||
grid.material.opacity = 0.2;
|
||||
grid.material.transparent = true;
|
||||
scene.add( grid );
|
||||
|
||||
|
||||
{
|
||||
var loader = new THREE.FontLoader();
|
||||
//导入字体,设定字体,这里的话,你们找对自己的字体路径,可能和我的不一样的!!下载的three.js包里面examples/fonts里面有字体
|
||||
loader.load('./yahei.json', function(font) {
|
||||
|
||||
// 文字
|
||||
var text = "Watting...";
|
||||
|
||||
var g = new THREE.TextGeometry(text, {
|
||||
// 设定文字字体,
|
||||
font: font,
|
||||
//尺寸
|
||||
size: 2,
|
||||
//厚度
|
||||
height: 1,
|
||||
});
|
||||
//计算边界,暂时不用管
|
||||
g.computeBoundingBox();
|
||||
|
||||
g = new THREE.EdgesGeometry(g); //或WireframeGeometry(几何)
|
||||
|
||||
var mat = new THREE.LineBasicMaterial({color : 0xffffff, linewidth : 2});
|
||||
|
||||
var wireframe = new THREE.LineSegments( g , mat );
|
||||
|
||||
scene.add(wireframe);
|
||||
|
||||
|
||||
})
|
||||
}
|
||||
|
||||
//获取点集
|
||||
getFontPoints('白狗','geo_ver',-23,0,0);
|
||||
getFontPoints('云平台','geo_ver2',-35,0,0)
|
||||
|
||||
|
||||
|
||||
//用点画字
|
||||
pointsMaterial = new THREE.PointsMaterial({
|
||||
color:0xffffff,
|
||||
size:0.5,
|
||||
transparent:true,//使材质透明
|
||||
blending:THREE.AdditiveBlending,
|
||||
depthTest:false,//深度测试关闭,不消去场景的不可见面
|
||||
map:createLightMateria()//刚刚创建的粒子贴图就在这里用上
|
||||
});
|
||||
|
||||
var originGeo = new THREE.Geometry();
|
||||
for (var i = 0; i <baseLens; i++){//循环创建Geo
|
||||
var x = basePoint[i].x;
|
||||
var y = basePoint[i].y;
|
||||
var z = basePoint[i].z;
|
||||
originGeo.vertices.push(new THREE.Vector3(x,y,z));
|
||||
}
|
||||
originParticleField = new THREE.Points(originGeo,pointsMaterial);
|
||||
// originParticleField.position.set(-20,10,0);
|
||||
scene.add(originParticleField);
|
||||
|
||||
}
|
||||
//获取 文字的点集
|
||||
function getFontPoints(txt,type,x,y,z){
|
||||
if(!x){var x=0;}
|
||||
if(!y){var y=0;}
|
||||
if(!z){var z=0;}
|
||||
var move =true;
|
||||
if(x==0&&y==0&&z==0){move = false;}
|
||||
var res = [];
|
||||
var loader = new THREE.FontLoader();
|
||||
loader.load("./yahei.json",function(font){
|
||||
// var gem2 = new THREE.TextGeometry(txt, {
|
||||
// size: 16, //字号大小,一般为大写字母的高度
|
||||
// height: 0.5, //文字的厚度
|
||||
// weight: 'bold', //值为'normal'或'bold',表示是否加粗
|
||||
// font: font, //字体,默认是'helvetiker',需对应引用的字体文件
|
||||
// style: 'normal', //值为'normal'或'italics',表示是否斜体
|
||||
// bevelThickness: 0.5, //倒角厚度
|
||||
// bevelSize: 0.5, //倒角宽度
|
||||
// curveSegments: 8,//弧线分段数,使得文字的曲线更加光滑
|
||||
// bevelEnabled: true, //布尔值,是否使用倒角,意为在边缘处斜切
|
||||
// });
|
||||
//
|
||||
// //计算边界
|
||||
// gem2.computeBoundingBox();
|
||||
|
||||
// var gem2 = new THREE.TextGeometry(txt, {
|
||||
// // 设定文字字体,
|
||||
// font: font,
|
||||
// //尺寸
|
||||
// size: 2,
|
||||
// //厚度
|
||||
// height: 1,
|
||||
// });
|
||||
|
||||
var shapes = font.generateShapes( txt, 2 );
|
||||
|
||||
var geometry = new THREE.ShapeBufferGeometry( shapes );
|
||||
|
||||
geometry.computeBoundingBox();
|
||||
|
||||
// 取线框图
|
||||
// EdgesGeometry
|
||||
var g = new THREE.WireframeGeometry(geometry);
|
||||
|
||||
// console.log("res = g.position", g.position)
|
||||
res = g.attributes.position.array;
|
||||
console.log("res", res.length)
|
||||
//字体一般不是居中的,需要手动调下
|
||||
if(move){
|
||||
var lens= res.length;
|
||||
var attrs = [];
|
||||
for(var i=0;i<lens;i++){
|
||||
var obj = {
|
||||
x:res[i].x+x,
|
||||
y:res[i].y+y,
|
||||
z:res[i].z+z,
|
||||
}
|
||||
attrs.push(obj);
|
||||
}
|
||||
res = attrs;
|
||||
}
|
||||
|
||||
switch(type){
|
||||
case 'geo_ver':
|
||||
geo_ver = res;
|
||||
break;
|
||||
case 'geo_ver2':
|
||||
geo_ver2 = res;
|
||||
break;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
function pointMove(position1){
|
||||
//移除粒子浮动动画
|
||||
// TWEEN.removeAll();
|
||||
var pointNow = originParticleField.geometry.vertices;
|
||||
var lens0 = position1.length;
|
||||
var pos = {val:1};
|
||||
var callback=function(){
|
||||
var val = this.val;
|
||||
var particles = originParticleField.geometry.vertices;
|
||||
// return console.log(particles);
|
||||
for(var i = 0; i < baseLens; i++) {
|
||||
var pos = particles[i];
|
||||
|
||||
if(i<lens0){
|
||||
pos.x = pointNow[i].x * val + position1[i].x * (1-val);
|
||||
pos.y = pointNow[i].y * val + position1[i].y * (1-val);
|
||||
pos.z = pointNow[i].z * val + position1[i].z * (1-val);
|
||||
}else{
|
||||
pos.x = pointNow[i].x * val + basePoint[i].x * (1-val);
|
||||
pos.y = pointNow[i].y * val + basePoint[i].y * (1-val);
|
||||
pos.z = pointNow[i].z * val + basePoint[i].z * (1-val);
|
||||
}
|
||||
}
|
||||
originParticleField.geometry.verticesNeedUpdate = true;
|
||||
}
|
||||
tween = new TWEEN.Tween(pos).to({val: 0}, 2000).easing(TWEEN.Easing.Quadratic.InOut).delay(500).onUpdate(callback);
|
||||
tween.start();
|
||||
}
|
||||
//粒子浮动动画
|
||||
|
||||
//绘制粒子贴图,
|
||||
function createLightMateria() {
|
||||
var canvasDom = document.createElement('canvas');
|
||||
canvasDom.width = 16;
|
||||
canvasDom.height = 16;
|
||||
var ctx = canvasDom.getContext('2d');
|
||||
//根据参数确定两个圆的坐标,绘制放射性渐变的方法,一个圆在里面,一个圆在外面
|
||||
var gradient = ctx.createRadialGradient(
|
||||
canvasDom.width/2,
|
||||
canvasDom.height/2,
|
||||
0,
|
||||
canvasDom.width/2,
|
||||
canvasDom.height/2,
|
||||
canvasDom.width/2);
|
||||
|
||||
gradient.addColorStop(0,'rgba(255,255,255,1)');
|
||||
gradient.addColorStop(0.005,'rgba(139,69,19,1)');
|
||||
gradient.addColorStop(0.4,'rgba(139,69,19,1)');
|
||||
gradient.addColorStop(1,'rgba(0,0,0,1)');
|
||||
|
||||
//设置颜色为渐变
|
||||
ctx.fillStyle = gradient;
|
||||
//绘图
|
||||
ctx.fillRect(0,0,canvasDom.width,canvasDom.height);
|
||||
|
||||
//贴图使用
|
||||
let texture = new THREE.Texture(canvasDom);
|
||||
texture.needsUpdate = true;//使用贴图时进行更新
|
||||
return texture;
|
||||
}
|
||||
|
||||
//初始化性能插件
|
||||
function initStats() {
|
||||
stats = new Stats();
|
||||
document.body.appendChild(stats.domElement);
|
||||
}
|
||||
|
||||
function initControls() {
|
||||
|
||||
controls = new THREE.OrbitControls(camera, renderer.domElement);
|
||||
//设置控制器的中心点
|
||||
controls.target.set( 0, 5, 0 );
|
||||
// 如果使用animate方法时,将此函数删除
|
||||
//controls.addEventListener( 'change', render );
|
||||
// 使动画循环使用时阻尼或自转 意思是否有惯性
|
||||
controls.enableDamping = true;
|
||||
//动态阻尼系数 就是鼠标拖拽旋转灵敏度
|
||||
//controls.dampingFactor = 0.25;
|
||||
//是否可以缩放
|
||||
controls.enableZoom = true;
|
||||
//是否自动旋转
|
||||
controls.autoRotate = false;
|
||||
controls.autoRotateSpeed = 0.5;
|
||||
//设置相机距离原点的最远距离
|
||||
controls.minDistance = 1;
|
||||
//设置相机距离原点的最远距离
|
||||
controls.maxDistance = 2000;
|
||||
//是否开启右键拖拽
|
||||
controls.enablePan = true;
|
||||
}
|
||||
|
||||
function render() {
|
||||
controls.update();
|
||||
}
|
||||
|
||||
//窗口变动触发的函数
|
||||
function onWindowResize() {
|
||||
|
||||
camera.aspect = window.innerWidth / window.innerHeight;
|
||||
camera.updateProjectionMatrix();
|
||||
renderer.setSize(window.innerWidth, window.innerHeight);
|
||||
|
||||
}
|
||||
|
||||
function animate() {
|
||||
//更新控制器
|
||||
render();
|
||||
|
||||
//更新性能插件
|
||||
stats.update();
|
||||
|
||||
TWEEN.update();
|
||||
|
||||
renderer.render(scene, camera);
|
||||
|
||||
requestAnimationFrame(animate);
|
||||
}
|
||||
|
||||
function draw() {
|
||||
//兼容性判断
|
||||
if (!Detector.webgl) Detector.addGetWebGLMessage();
|
||||
|
||||
initGui();
|
||||
initRender();
|
||||
initScene();
|
||||
initCamera();
|
||||
initLight();
|
||||
initModel();
|
||||
initControls();
|
||||
initStats();
|
||||
|
||||
animate();
|
||||
window.onresize = onWindowResize;
|
||||
}
|
||||
|
||||
var t = 0
|
||||
setInterval(function () {
|
||||
|
||||
if ( 0 == t ){
|
||||
pointMove(geo_ver);
|
||||
t = 1
|
||||
} else {
|
||||
t = 0
|
||||
pointMove(geo_ver2);
|
||||
}
|
||||
|
||||
|
||||
}, 3000 )
|
||||
|
||||
|
||||
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,494 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<meta name="full-screen" content="yes">
|
||||
<meta name="browsermode" content="application">
|
||||
<meta name="x5-orientation" content="portrait">
|
||||
<meta name="x5-fullscreen" content="true">
|
||||
<meta name="x5-page-mode" content="app">
|
||||
<meta name="viewport" content="width=device-width,initial-scale=1.0, minimum-scale=1.0, maximum-scale=1.0, user-scalable=no,minimal-ui">
|
||||
<meta name="apple-mobile-web-app-capable" content="yes" />
|
||||
<meta name="apple-mobile-web-app-status-bar-style" content="black-translucent" />
|
||||
|
||||
<meta name="apple-mobile-web-app-title" content="应用标题">
|
||||
<meta content="telephone=no" name="format-detection" />
|
||||
<meta content="email=no" name="format-detection" />
|
||||
|
||||
|
||||
|
||||
<title>VR 亿企云平台</title>
|
||||
</head>
|
||||
<body onload="draw();">
|
||||
|
||||
|
||||
<div style="position: fixed;">
|
||||
<div id="moAccel"></div>
|
||||
<div id="moCalcTiltLR"></div>
|
||||
<div id="moCalcTiltFB"></div>
|
||||
<div id="imgLogo">-----------------</div>
|
||||
|
||||
<div id="arrow"></div>
|
||||
<div id="acceleration"></div>
|
||||
</div>
|
||||
|
||||
<script type="application/javascript">
|
||||
|
||||
(function () {
|
||||
var arrow = document.getElementById("arrow");
|
||||
try {
|
||||
var text = "";
|
||||
window.addEventListener("deviceorientation", orientationHandler, false);
|
||||
function orientationHandler(event) {
|
||||
text = ""
|
||||
|
||||
text += "左右旋转:rotate alpha{" + Math.round(event.alpha) + "deg)<br>";
|
||||
text += "前后旋转:rotate beta{" + Math.round(event.beta) + "deg)<br>";
|
||||
text += "扭转设备:rotate gamma{" + Math.round(event.gamma) + "deg)<br>";
|
||||
arrow.innerHTML = text;
|
||||
}
|
||||
}
|
||||
catch (e) {
|
||||
arrow.innerHTML = e.message
|
||||
}
|
||||
})()
|
||||
|
||||
</script>
|
||||
<script type="application/javascript">
|
||||
|
||||
var vx = vy = vz = 0; //用以获取xyz轴当前的数据
|
||||
var sx = sy = sz = 0;
|
||||
|
||||
var startTime = new Date().getTime(); // 最初的开始时间,单位:毫秒
|
||||
|
||||
function deviceMotionHandler2(eventData) {
|
||||
// 捕捉重力加速度
|
||||
var acceleration = eventData.accelerationIncludingGravity;
|
||||
// 打印加速数据
|
||||
var rawAcceleration = "[" + Math.round(acceleration.x) + ", " +Math.round(acceleration.y) + ", " + Math.round(acceleration.z) + "]";
|
||||
// Z轴,可知设备朝上或者朝下
|
||||
var facingUp = -1;
|
||||
if (acceleration.z > 0) {
|
||||
facingUp = +1;
|
||||
}
|
||||
// 根据重力通过 acceleration.x|y 转换得到加速值,
|
||||
// 运用重力加速度9.81来计算得到一个百分比然后乘以转换角度90
|
||||
var tiltLR = Math.round(((acceleration.x) / 9.81) * -90);
|
||||
var tiltFB = Math.round(((acceleration.y + 9.81) / 9.81) * 90 * facingUp);
|
||||
// 打印加速度的计算结果
|
||||
document.getElementById("moAccel").innerHTML = rawAcceleration;
|
||||
document.getElementById("moCalcTiltLR").innerHTML = tiltLR;
|
||||
document.getElementById("moCalcTiltFB").innerHTML = tiltFB;
|
||||
// 将2D和3D的转换应用到图片上
|
||||
var rotation = "rotate(" + tiltLR + "deg) (1,0,0, " + (tiltFB) + "deg)";
|
||||
document.getElementById("imgLogo").innerHTML = rotation;
|
||||
}
|
||||
|
||||
if (window.DeviceMotionEvent) {
|
||||
|
||||
window.addEventListener('devicemotion', function deviceMotionHandler(eventData){
|
||||
deviceMotionHandler2(eventData)
|
||||
|
||||
// document.getElementById("acceleration").innerText = "dz = " + eventData.acceleration.x.toFixed(2) + " " + eventData.accelerationIncludingGravity.x.toFixed(2)
|
||||
var currTime = new Date().getTime(); //当前时间
|
||||
|
||||
var diffTime = currTime - startTime;//当前时间减最初时间,得到当前时间差
|
||||
|
||||
|
||||
var acceleration = eventData.acceleration; //获得加速器对象
|
||||
|
||||
var x = acceleration.x
|
||||
var y = acceleration.y
|
||||
var z = acceleration.z
|
||||
vx += x; //获取x轴当前加速度
|
||||
|
||||
vy += y; //获取y轴当前加速度
|
||||
|
||||
vz += z; //获取z轴当前加速度
|
||||
|
||||
sx += diffTime * vx
|
||||
sy += diffTime * vy
|
||||
sz += diffTime * vz
|
||||
|
||||
|
||||
document.getElementById("acceleration").innerText = "\r\n" +
|
||||
"x = " + x.toFixed(2) + "\n" +
|
||||
"y = " + y.toFixed(2) + "\n" +
|
||||
"z = " + z.toFixed(2) + "\n" +
|
||||
"vx = " + vx.toFixed(2) + "\n" +
|
||||
"vy = " + vy.toFixed(2) + "\n" +
|
||||
"vz = " + vz.toFixed(2) + "\n" +
|
||||
"sx = " + sx.toFixed(2) + "\n" +
|
||||
"sy = " + sy.toFixed(2) + "\n" +
|
||||
"sz = " + sz.toFixed(2) + "\n" +
|
||||
"\n";
|
||||
|
||||
}, false);
|
||||
|
||||
}
|
||||
|
||||
</script>
|
||||
|
||||
<script src="./three.js"></script>
|
||||
<script src="./lib/OrbitControls.js"></script>
|
||||
<script src="./stats.min.js"></script>
|
||||
<script src="./lib/dat.gui.min.js"></script>
|
||||
<script src="./lib/Detector.js"></script>
|
||||
<script src="./lib/tween.min.js"></script>
|
||||
|
||||
|
||||
<script>
|
||||
var renderer, camera, scene, gui, light, stats, controls;
|
||||
//字体的点集
|
||||
var originParticleField,pointsMaterial,geo_ver,geo_ver2,tween,hearts=[];
|
||||
//初始点
|
||||
var baseLens =10000,basePoint=[],baseArea=160;
|
||||
for(var i=0;i<baseLens;i++){
|
||||
var x= Number(Math.random()*baseArea)-baseArea/2;
|
||||
var y= Number(Math.random()*baseArea)-baseArea/2;
|
||||
var z= Number(Math.random()*baseArea)-baseArea/2;
|
||||
var obj = {
|
||||
x:x,
|
||||
y:y,
|
||||
z:z
|
||||
}
|
||||
basePoint.push(obj);
|
||||
}
|
||||
|
||||
|
||||
|
||||
function initRender() {
|
||||
renderer = new THREE.WebGLRenderer({antialias: true});
|
||||
renderer.setPixelRatio(window.devicePixelRatio);
|
||||
renderer.setSize(window.innerWidth, window.innerHeight);
|
||||
renderer.setClearColor(0xeeeeee);
|
||||
renderer.shadowMap.enabled = true;
|
||||
//告诉渲染器需要阴影效果
|
||||
document.body.appendChild(renderer.domElement);
|
||||
}
|
||||
|
||||
function initCamera() {
|
||||
camera = new THREE.PerspectiveCamera(45, window.innerWidth / window.innerHeight, 0.1, 200);
|
||||
camera.position.set(0, 20, 80 );
|
||||
}
|
||||
|
||||
function initScene() {
|
||||
scene = new THREE.Scene();
|
||||
scene.background = new THREE.Color( 0xa0a0a0 );
|
||||
scene.fog = new THREE.Fog( 0xa0a0a0, 5, 250 );
|
||||
}
|
||||
|
||||
//初始化dat.GUI简化试验流程
|
||||
function initGui() {
|
||||
// //声明一个保存需求修改的相关数据的对象
|
||||
// gui = {
|
||||
// bump:0.03,
|
||||
// animation:false
|
||||
// };
|
||||
// var datGui = new dat.GUI();
|
||||
// //将设置属性添加到gui当中,gui.add(对象,属性,最小值,最大值)
|
||||
// datGui.add(gui, "bump", -1, 1).onChange(function (e) {
|
||||
// cube1.material.bumpScale = e;
|
||||
// });
|
||||
//
|
||||
// datGui.add(gui, "animation");
|
||||
}
|
||||
|
||||
function initLight() {
|
||||
scene.add(new THREE.AmbientLight(0x444444));
|
||||
|
||||
light = new THREE.DirectionalLight(0xffffff);
|
||||
light.position.set(0, 600, 240 );
|
||||
|
||||
light.castShadow = true;
|
||||
light.shadow.camera.top = 10;
|
||||
light.shadow.camera.bottom = -10;
|
||||
light.shadow.camera.left = -10;
|
||||
light.shadow.camera.right = 10;
|
||||
|
||||
//告诉平行光需要开启阴影投射
|
||||
light.castShadow = true;
|
||||
|
||||
// scene.add(light);
|
||||
}
|
||||
|
||||
function initModel() {
|
||||
|
||||
//辅助工具
|
||||
var helper = new THREE.AxesHelper(50);
|
||||
scene.add(helper);
|
||||
|
||||
// 地板
|
||||
var mesh = new THREE.Mesh( new THREE.PlaneBufferGeometry( 400, 400 ), new THREE.MeshPhongMaterial( { color: 0xffffff, depthWrite: false } ) );
|
||||
mesh.rotation.x = - Math.PI / 2;
|
||||
mesh.receiveShadow = true;
|
||||
scene.add( mesh );
|
||||
|
||||
//添加地板割线
|
||||
var grid = new THREE.GridHelper( 400, 50, 0x000000, 0x000000 );
|
||||
grid.material.opacity = 0.2;
|
||||
grid.material.transparent = true;
|
||||
scene.add( grid );
|
||||
|
||||
|
||||
{
|
||||
var loader = new THREE.FontLoader();
|
||||
//导入字体,设定字体,这里的话,你们找对自己的字体路径,可能和我的不一样的!!下载的three.js包里面examples/fonts里面有字体
|
||||
loader.load('./yahei.json', function(font) {
|
||||
|
||||
// 文字
|
||||
var text = "银企云平台";
|
||||
|
||||
var g = new THREE.TextGeometry(text, {
|
||||
// 设定文字字体,
|
||||
font: font,
|
||||
//尺寸
|
||||
size: 15,
|
||||
//厚度
|
||||
height: 5,
|
||||
});
|
||||
//计算边界,暂时不用管
|
||||
g.computeBoundingBox();
|
||||
|
||||
g = new THREE.EdgesGeometry(g); //或 WireframeGeometry(几何)
|
||||
|
||||
var mat = new THREE.LineBasicMaterial({color : 0xffffff, linewidth : 5});
|
||||
|
||||
var wireframe = new THREE.LineSegments( g , mat );
|
||||
|
||||
wireframe.position.set( -50, 0, 0);
|
||||
|
||||
scene.add(wireframe);
|
||||
|
||||
|
||||
})
|
||||
}
|
||||
|
||||
}
|
||||
//获取 文字的点集
|
||||
function getFontPoints(txt,type,x,y,z){
|
||||
if(!x){var x=0;}
|
||||
if(!y){var y=0;}
|
||||
if(!z){var z=0;}
|
||||
var move =true;
|
||||
if(x==0&&y==0&&z==0){move = false;}
|
||||
var res = [];
|
||||
var loader = new THREE.FontLoader();
|
||||
loader.load("./yahei.json",function(font){
|
||||
// var gem2 = new THREE.TextGeometry(txt, {
|
||||
// size: 16, //字号大小,一般为大写字母的高度
|
||||
// height: 0.5, //文字的厚度
|
||||
// weight: 'bold', //值为'normal'或'bold',表示是否加粗
|
||||
// font: font, //字体,默认是'helvetiker',需对应引用的字体文件
|
||||
// style: 'normal', //值为'normal'或'italics',表示是否斜体
|
||||
// bevelThickness: 0.5, //倒角厚度
|
||||
// bevelSize: 0.5, //倒角宽度
|
||||
// curveSegments: 8,//弧线分段数,使得文字的曲线更加光滑
|
||||
// bevelEnabled: true, //布尔值,是否使用倒角,意为在边缘处斜切
|
||||
// });
|
||||
//
|
||||
// //计算边界
|
||||
// gem2.computeBoundingBox();
|
||||
|
||||
// var gem2 = new THREE.TextGeometry(txt, {
|
||||
// // 设定文字字体,
|
||||
// font: font,
|
||||
// //尺寸
|
||||
// size: 2,
|
||||
// //厚度
|
||||
// height: 1,
|
||||
// });
|
||||
|
||||
var shapes = font.generateShapes( txt, 2 );
|
||||
|
||||
var geometry = new THREE.ShapeBufferGeometry( shapes );
|
||||
|
||||
geometry.computeBoundingBox();
|
||||
|
||||
// 取线框图
|
||||
// EdgesGeometry
|
||||
var g = new THREE.WireframeGeometry(geometry);
|
||||
|
||||
// console.log("res = g.position", g.position)
|
||||
res = g.attributes.position.array;
|
||||
console.log("res", res.length)
|
||||
//字体一般不是居中的,需要手动调下
|
||||
if(move){
|
||||
var lens= res.length;
|
||||
var attrs = [];
|
||||
for(var i=0;i<lens;i++){
|
||||
var obj = {
|
||||
x:res[i].x+x,
|
||||
y:res[i].y+y,
|
||||
z:res[i].z+z,
|
||||
}
|
||||
attrs.push(obj);
|
||||
}
|
||||
res = attrs;
|
||||
}
|
||||
|
||||
switch(type){
|
||||
case 'geo_ver':
|
||||
geo_ver = res;
|
||||
break;
|
||||
case 'geo_ver2':
|
||||
geo_ver2 = res;
|
||||
break;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
function pointMove(position1){
|
||||
//移除粒子浮动动画
|
||||
// TWEEN.removeAll();
|
||||
var pointNow = originParticleField.geometry.vertices;
|
||||
var lens0 = position1.length;
|
||||
var pos = {val:1};
|
||||
var callback=function(){
|
||||
var val = this.val;
|
||||
var particles = originParticleField.geometry.vertices;
|
||||
// return console.log(particles);
|
||||
for(var i = 0; i < baseLens; i++) {
|
||||
var pos = particles[i];
|
||||
|
||||
if(i<lens0){
|
||||
pos.x = pointNow[i].x * val + position1[i].x * (1-val);
|
||||
pos.y = pointNow[i].y * val + position1[i].y * (1-val);
|
||||
pos.z = pointNow[i].z * val + position1[i].z * (1-val);
|
||||
}else{
|
||||
pos.x = pointNow[i].x * val + basePoint[i].x * (1-val);
|
||||
pos.y = pointNow[i].y * val + basePoint[i].y * (1-val);
|
||||
pos.z = pointNow[i].z * val + basePoint[i].z * (1-val);
|
||||
}
|
||||
}
|
||||
originParticleField.geometry.verticesNeedUpdate = true;
|
||||
}
|
||||
tween = new TWEEN.Tween(pos).to({val: 0}, 2000).easing(TWEEN.Easing.Quadratic.InOut).delay(500).onUpdate(callback);
|
||||
tween.start();
|
||||
}
|
||||
//粒子浮动动画
|
||||
|
||||
//绘制粒子贴图,
|
||||
function createLightMateria() {
|
||||
var canvasDom = document.createElement('canvas');
|
||||
canvasDom.width = 16;
|
||||
canvasDom.height = 16;
|
||||
var ctx = canvasDom.getContext('2d');
|
||||
//根据参数确定两个圆的坐标,绘制放射性渐变的方法,一个圆在里面,一个圆在外面
|
||||
var gradient = ctx.createRadialGradient(
|
||||
canvasDom.width/2,
|
||||
canvasDom.height/2,
|
||||
0,
|
||||
canvasDom.width/2,
|
||||
canvasDom.height/2,
|
||||
canvasDom.width/2);
|
||||
|
||||
gradient.addColorStop(0,'rgba(255,255,255,1)');
|
||||
gradient.addColorStop(0.005,'rgba(139,69,19,1)');
|
||||
gradient.addColorStop(0.4,'rgba(139,69,19,1)');
|
||||
gradient.addColorStop(1,'rgba(0,0,0,1)');
|
||||
|
||||
//设置颜色为渐变
|
||||
ctx.fillStyle = gradient;
|
||||
//绘图
|
||||
ctx.fillRect(0,0,canvasDom.width,canvasDom.height);
|
||||
|
||||
//贴图使用
|
||||
let texture = new THREE.Texture(canvasDom);
|
||||
texture.needsUpdate = true;//使用贴图时进行更新
|
||||
return texture;
|
||||
}
|
||||
|
||||
//初始化性能插件
|
||||
function initStats() {
|
||||
stats = new Stats();
|
||||
document.body.appendChild(stats.domElement);
|
||||
}
|
||||
|
||||
function initControls() {
|
||||
|
||||
controls = new THREE.OrbitControls(camera, renderer.domElement);
|
||||
//设置控制器的中心点
|
||||
controls.target.set( 0, 5, 0 );
|
||||
// 如果使用animate方法时,将此函数删除
|
||||
//controls.addEventListener( 'change', render );
|
||||
// 使动画循环使用时阻尼或自转 意思是否有惯性
|
||||
controls.enableDamping = true;
|
||||
//动态阻尼系数 就是鼠标拖拽旋转灵敏度
|
||||
//controls.dampingFactor = 0.25;
|
||||
//是否可以缩放
|
||||
controls.enableZoom = true;
|
||||
//是否自动旋转
|
||||
controls.autoRotate = false;
|
||||
controls.autoRotateSpeed = 0.5;
|
||||
//设置相机距离原点的最远距离
|
||||
controls.minDistance = 1;
|
||||
//设置相机距离原点的最远距离
|
||||
controls.maxDistance = 2000;
|
||||
//是否开启右键拖拽
|
||||
controls.enablePan = true;
|
||||
}
|
||||
|
||||
function render() {
|
||||
controls.update();
|
||||
}
|
||||
|
||||
//窗口变动触发的函数
|
||||
function onWindowResize() {
|
||||
|
||||
camera.aspect = window.innerWidth / window.innerHeight;
|
||||
camera.updateProjectionMatrix();
|
||||
renderer.setSize(window.innerWidth, window.innerHeight);
|
||||
|
||||
}
|
||||
|
||||
function animate() {
|
||||
//更新控制器
|
||||
render();
|
||||
|
||||
//更新性能插件
|
||||
stats.update();
|
||||
|
||||
TWEEN.update();
|
||||
|
||||
renderer.render(scene, camera);
|
||||
|
||||
requestAnimationFrame(animate);
|
||||
}
|
||||
|
||||
function draw() {
|
||||
//兼容性判断
|
||||
if (!Detector.webgl) Detector.addGetWebGLMessage();
|
||||
|
||||
initGui();
|
||||
initRender();
|
||||
initScene();
|
||||
initCamera();
|
||||
initLight();
|
||||
initModel();
|
||||
initControls();
|
||||
initStats();
|
||||
|
||||
animate();
|
||||
window.onresize = onWindowResize;
|
||||
}
|
||||
|
||||
// var t = 0
|
||||
// setInterval(function () {
|
||||
//
|
||||
// if ( 0 == t ){
|
||||
// pointMove(geo_ver);
|
||||
// t = 1
|
||||
// } else {
|
||||
// t = 0
|
||||
// pointMove(geo_ver2);
|
||||
// }
|
||||
//
|
||||
//
|
||||
// }, 3000 )
|
||||
|
||||
|
||||
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
File diff suppressed because one or more lines are too long
@@ -0,0 +1,263 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>Logo - 全栈工程师俱乐部</title>
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<div style="border: 10px dotted #EEE; width:600px">
|
||||
<h1>方案 1 </h1>
|
||||
<canvas id="zdog1" width="500" height="500"></canvas>
|
||||
</div>
|
||||
|
||||
|
||||
<div style="border: 10px dotted #EEE; width:600px; background: #00b7ee">
|
||||
<h1>方案 2 </h1>
|
||||
<canvas id="zdog2" width="500" height="500"></canvas>
|
||||
</div>
|
||||
|
||||
|
||||
<div style="border: 10px dotted #EEE; width:600px">
|
||||
<h1>方案 3 </h1>
|
||||
<canvas id="zdog3" width="500" height="500"></canvas>
|
||||
</div>
|
||||
|
||||
<canvas id="zdog" width="500" height="500"></canvas>
|
||||
|
||||
|
||||
|
||||
<!--引入zdog文件-->
|
||||
<script src="https://unpkg.com/zdog@1/dist/zdog.dist.min.js"></script>
|
||||
<script type="application/javascript">
|
||||
|
||||
|
||||
class Yun extends Zdog.Shape {
|
||||
constructor( options ){
|
||||
|
||||
options.path = [
|
||||
{ x: -0.6 , y : -0.5 }, // start at 1st point
|
||||
{ x: 0.6 , y : -0.5 }, // line to 2nd point
|
||||
{ move: {x: -0.8 , y: 0} },
|
||||
{ x: 0.8 , y: 0},
|
||||
{ move: {x: 0, y: 0} },
|
||||
{ x: -0.5, y: 0.7 },
|
||||
{ x: 0.4, y: 0.6 },
|
||||
{ move: {x: 0.4, y: 0.5} },
|
||||
{ x: 0.6, y: 0.7 },
|
||||
],
|
||||
super(options);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
Zdog.Yun = Yun
|
||||
</script>
|
||||
|
||||
|
||||
<script>
|
||||
(function () {
|
||||
|
||||
var sceneSize = 500;
|
||||
var TAU = Zdog.TAU;
|
||||
var ROOT2 = Math.sqrt(2);
|
||||
var ROOT3 = Math.sqrt(3);
|
||||
var ROOT5 = Math.sqrt(5);
|
||||
var PHI = ( 1 + ROOT5 ) / 2;
|
||||
|
||||
// colors
|
||||
var color = '#FA5';
|
||||
|
||||
var newcanvas = new Zdog.Illustration({
|
||||
// 用id选择器设置画布
|
||||
element: '#zdog1',
|
||||
dragRotate: true,
|
||||
});
|
||||
|
||||
// var yun = new Zdog.Yun({
|
||||
// addTo: newcanvas,
|
||||
// stroke: 20,
|
||||
// color: '#636',
|
||||
// });
|
||||
|
||||
new Zdog.Yun({
|
||||
addTo: newcanvas,
|
||||
closed: false,
|
||||
stroke: 20,
|
||||
scale : 50,
|
||||
color: '#636',
|
||||
});
|
||||
|
||||
|
||||
function animate() {
|
||||
|
||||
// 通过逐步增加xxx.rotate.y来改变场景的旋转。值越大越快。
|
||||
newcanvas.rotate.y += 0.01;
|
||||
// newcanvas.rotate.x += 0.02;
|
||||
newcanvas.updateRenderGraph();
|
||||
// 动画下一帧继续执行函数
|
||||
requestAnimationFrame( animate );
|
||||
}
|
||||
// 开始动画,执行函数
|
||||
animate();
|
||||
})()
|
||||
|
||||
</script>
|
||||
|
||||
|
||||
<script>
|
||||
// 方案二
|
||||
|
||||
( function() {
|
||||
var beigeDark = '#F96';
|
||||
var beigeLight = '#FC9';
|
||||
var skinDark = '#F66';
|
||||
var skinMedium = '#F88';
|
||||
var skinLight = '#FAA';
|
||||
var navy = '#036';
|
||||
var midnight = '#003';
|
||||
var auburn = '#903';
|
||||
var red = '#C33';
|
||||
var sky = '#09D';
|
||||
var offWhite = '#FFD';
|
||||
var white = 'white';
|
||||
var blueDark = '#66C';
|
||||
var bluePale = '#CCF';
|
||||
var TAU = Zdog.TAU;
|
||||
var sceneStartRotation = { y: -TAU/8 };
|
||||
var newcanvas = new Zdog.Illustration({
|
||||
// 用id选择器设置画布
|
||||
element: '#zdog2',
|
||||
dragRotate: true,
|
||||
});
|
||||
|
||||
// big puff
|
||||
var cloud = new Zdog.Shape({
|
||||
addTo: newcanvas,
|
||||
translate: { x: 34, y: -26, z: -20 },
|
||||
rotate: { y: -sceneStartRotation.y },
|
||||
stroke: 16,
|
||||
color: white,
|
||||
// scale : 5,
|
||||
});
|
||||
|
||||
// left small puff
|
||||
var smallPuff = new Zdog.Shape({
|
||||
addTo: cloud,
|
||||
translate: { x: -9, y: 4, z: 4 },
|
||||
stroke: 8,
|
||||
color: white,
|
||||
});
|
||||
smallPuff.copy({
|
||||
translate: { x: 9, y: 5, z: 6 },
|
||||
stroke: 10,
|
||||
});
|
||||
|
||||
var disk = new Zdog.RoundedRect({
|
||||
addTo: cloud,
|
||||
width: 26,
|
||||
height: 12,
|
||||
cornerRadius: 6,
|
||||
translate: { x: -6, y: 7, z: 4 },
|
||||
rotate: { x: TAU/4 },
|
||||
stroke: 3,
|
||||
color: white,
|
||||
fill: true,
|
||||
});
|
||||
disk.copy({
|
||||
translate: { x: 6, y: 9, z: 8 },
|
||||
});
|
||||
|
||||
// sun
|
||||
new Zdog.Shape({
|
||||
addTo: cloud,
|
||||
translate: { x: -13, y: 0, z: -14 },
|
||||
stroke: 8,
|
||||
color: beigeLight,
|
||||
});
|
||||
|
||||
|
||||
function animate() {
|
||||
|
||||
// 通过逐步增加xxx.rotate.y来改变场景的旋转。值越大越快。
|
||||
newcanvas.rotate.y += 0.01;
|
||||
// newcanvas.rotate.x += 0.02;
|
||||
newcanvas.updateRenderGraph();
|
||||
// 动画下一帧继续执行函数
|
||||
requestAnimationFrame( animate );
|
||||
}
|
||||
// 开始动画,执行函数
|
||||
animate();
|
||||
|
||||
})();
|
||||
|
||||
</script>
|
||||
|
||||
<script>
|
||||
|
||||
(function () {
|
||||
|
||||
// Made with Zdog
|
||||
|
||||
const TAU = Zdog.TAU;
|
||||
let isSpinning = true;
|
||||
|
||||
let illo = new Zdog.Illustration({
|
||||
element: '#zdog3',
|
||||
rotate: { x: -TAU/16},
|
||||
dragRotate: true,
|
||||
onDragStart: function() {
|
||||
isSpinning = false;
|
||||
},
|
||||
});
|
||||
|
||||
var rotor = new Zdog.Anchor({
|
||||
addTo: illo,
|
||||
});
|
||||
|
||||
new Zdog.Rect({
|
||||
addTo: rotor,
|
||||
width: 80,
|
||||
height: 60,
|
||||
translate: { z: 50 },
|
||||
stroke: 8,
|
||||
fill: true,
|
||||
color: '#EA0',
|
||||
// backface color
|
||||
backface: '#636',
|
||||
});
|
||||
|
||||
new Zdog.Yun({
|
||||
addTo: rotor,
|
||||
closed: false,
|
||||
stroke: 8,
|
||||
scale : 25,
|
||||
translate: { z: 60 },
|
||||
color: '#636',
|
||||
});
|
||||
|
||||
rotor.copyGraph({
|
||||
rotate: { y: TAU * 1/4 },
|
||||
});
|
||||
rotor.copyGraph({
|
||||
rotate: { y: TAU * 2/4 },
|
||||
});
|
||||
rotor.copyGraph({
|
||||
rotate: { y: TAU * 3/4 },
|
||||
});
|
||||
|
||||
function animate() {
|
||||
illo.rotate.y += isSpinning ? 0.03 : 0;
|
||||
illo.updateRenderGraph();
|
||||
requestAnimationFrame( animate );
|
||||
}
|
||||
|
||||
animate();
|
||||
|
||||
})()
|
||||
|
||||
</script>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
@@ -0,0 +1,357 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>IC 卡维护工具</title>
|
||||
<style>
|
||||
:root {
|
||||
--mainColor: #0062cc;
|
||||
}
|
||||
|
||||
html, body {
|
||||
margin: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.title {
|
||||
color: var(--mainColor);
|
||||
}
|
||||
|
||||
.container {
|
||||
margin: 2rem auto;
|
||||
border: var(--mainColor) solid 2px;
|
||||
border-radius: 10px;
|
||||
width: 80%;
|
||||
height: 80%;
|
||||
text-align: left;
|
||||
}
|
||||
|
||||
.group {
|
||||
padding: 1rem;
|
||||
margin: 1rem;
|
||||
}
|
||||
|
||||
.form input {
|
||||
display: block;
|
||||
margin: 0.5rem 0;
|
||||
}
|
||||
|
||||
</style>
|
||||
<link rel="stylesheet" type="text/css" href="tabs.css">
|
||||
<link rel="stylesheet" type="text/css" href="layx.min.css">
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<div style="width: 100%; text-align: center;">
|
||||
<h2 class="title">信雅达 IC 卡发行工具</h2>
|
||||
</div>
|
||||
|
||||
<div class="container">
|
||||
|
||||
<div class="group" style="height: 10rem">
|
||||
<ul class="tabs">
|
||||
<li>
|
||||
<a href="#" name="tab_public">IC 卡发行</a>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<a href="#" name="tab_file">文件操作</a>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<a href="#" name="tab_pin">PIN 管理</a>
|
||||
</li>
|
||||
|
||||
|
||||
</ul>
|
||||
|
||||
<div class="tabs-content">
|
||||
|
||||
|
||||
<div class="tab tab_public">
|
||||
|
||||
<div class="form">
|
||||
|
||||
<input id="manufactor" style="width: 300px; height: 1.06rem" type="text" value=""
|
||||
placeholder="厂家标记">
|
||||
<input id="system" style="width: 300px; height: 1.06rem" type="text" value="" placeholder="系统信息">
|
||||
<input id="customer" style="width: 300px; height: 1.06rem" type="text" value="" placeholder="客户信息">
|
||||
|
||||
</div>
|
||||
|
||||
<div style="margin: 1rem 0 ">
|
||||
<button id="btn_nameplate_clear" style="margin-right: 1rem">清空</button>
|
||||
<button id="btn_nameplate_tmp_save" style="margin-right: 1rem">临存</button>
|
||||
<button id="btn_nameplate_tmp_load" style="margin-right: 1rem">临取</button>
|
||||
<button id="btn_nameplate_read" style="margin-right: 1rem">返显</button>
|
||||
</div>
|
||||
|
||||
<button id="btn_nameplate_release" style="margin-right: 1rem">发  行</button>
|
||||
|
||||
</div>
|
||||
|
||||
<div class="tab tab_file">
|
||||
|
||||
|
||||
<input id="path" style="width: 300px; height: 1.06rem" type="text" value="\root\mana"
|
||||
placeholder="文件目录">
|
||||
<button id="btn_list_path" style="margin-right: 1rem">枚  举</button>
|
||||
|
||||
<textarea id="ta_files" style="display: block; margin: 1rem 0; width: 375px; height: 100px;"
|
||||
readonly></textarea>
|
||||
|
||||
|
||||
<input id="filepath" style="width: 300px; height: 1.06rem" type="text" value="\root\mana\name"
|
||||
maxlength="6" placeholder="文件">
|
||||
<button id="btn_read" style="margin-right: 0.5rem">读</button>
|
||||
<button id="btn_write" style="margin-right: 1rem">写</button>
|
||||
|
||||
<textarea id="ta_txt" style="display: block; margin: 1rem 0; width: 375px; height: 100px;"
|
||||
readonly></textarea>
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
<div class="tab tab_pin">
|
||||
<div class="group" style="width: 100%; ">
|
||||
<input id="pwd2" style="width: 300px;height: 1.06rem" type="password" maxlength="8"
|
||||
placeholder="口令,8 个数字">
|
||||
<button id="login2" style="margin-right: 1rem">授  权</button>
|
||||
<button id="login_def2" style="margin-right: 1rem">默认口令</button>
|
||||
</div>
|
||||
|
||||
|
||||
<div class="form group">
|
||||
<input id="old_pwd" style="width: 360px;height: 1.06rem" type="password" maxlength="8"
|
||||
placeholder="旧口令,8 个数字">
|
||||
<input id="new_pwd1" style="width: 360px;height: 1.06rem" type="password" maxlength="8"
|
||||
placeholder="新口令,8 个数字">
|
||||
<input id="new_pwd2" style="width: 360px;height: 1.06rem" type="password" maxlength="8"
|
||||
placeholder="重复新口令,8 个数字">
|
||||
<button id="update1" style="margin-right: 1rem">修改操作员 PIN</button>
|
||||
<button id="update2" style="margin-right: 1rem">修改管理员 PIN</button>
|
||||
<button id="reset" style="margin-right: 1rem">解锁操作员 PIN</button>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<!-- UKey 支持, 共 3 个 js-->
|
||||
<!-- jquery -->
|
||||
<script type="text/javascript" src="./jquery.min.js"></script>
|
||||
<script type="text/javascript" src="./fiseckey.js"></script>
|
||||
<script type="text/javascript" src="./ukey.js"></script>
|
||||
|
||||
|
||||
<!-- 演示程序 -->
|
||||
<script type="text/javascript" src="./tabs.js"></script>
|
||||
<script type="application/javascript" src="layx.min.js"></script>
|
||||
<script type="application/javascript" src="tools.js"></script>
|
||||
<script type="application/javascript">
|
||||
$(function () {
|
||||
function refresh() {
|
||||
var list = window.UKey.enumDevByArray()
|
||||
if (list) {
|
||||
var ll = list.split("|");
|
||||
var options = ""
|
||||
for (var i = 0; i < ll.length; i++) {
|
||||
var value = ll[i].split(",")[0]
|
||||
options += "<option value =\"" + value + "\">" + ll[i] + "</option>"
|
||||
}
|
||||
$("#ukeys").html(options);
|
||||
}
|
||||
}
|
||||
|
||||
refresh();
|
||||
|
||||
$("#btn_refresh").click(function () {
|
||||
refresh()
|
||||
success("刷新成功")
|
||||
})
|
||||
|
||||
$("#btn_list_path").click(function () {
|
||||
var path = $("#path").val();
|
||||
try {
|
||||
var ret = window.UKey.enumDir(path)
|
||||
|
||||
var out = ""
|
||||
for (var i = 0; i < ret.folders.length; i++) {
|
||||
out += "文件夹:\t" + ret.folders[i] + "\r\n"
|
||||
}
|
||||
|
||||
for (var i = 0; i < ret.files.length; i++) {
|
||||
out += "文件:\t" + ret.files[i] + "\r\n"
|
||||
}
|
||||
|
||||
$("#ta_files").text(out)
|
||||
success("枚举成功")
|
||||
|
||||
} catch (e) {
|
||||
alert("枚举失败:" + e.message)
|
||||
}
|
||||
})
|
||||
|
||||
|
||||
$("#login2").click(function () {
|
||||
var pwd2 = $("#pwd2").val();
|
||||
check(pwd2, /\d{8}/, "口令输入错误")
|
||||
var ukey = $("#ukeys").val();
|
||||
|
||||
try {
|
||||
window.UKey.admin(ukey, pwd2)
|
||||
success("登录成功")
|
||||
} catch (e) {
|
||||
alert("登录失败:" + e.message)
|
||||
}
|
||||
})
|
||||
|
||||
$("#login2_def").click(function () {
|
||||
$("#pwd2").val("12345678");
|
||||
$("#login2").click()
|
||||
})
|
||||
|
||||
$("#login").click(function () {
|
||||
var pwd1 = $("#pwd1").val();
|
||||
check(pwd1, /\d{8}/, "口令输入错误")
|
||||
var ukey = $("#ukeys").val();
|
||||
|
||||
try {
|
||||
window.UKey.login(ukey, pwd1)
|
||||
success("登录成功")
|
||||
} catch (e) {
|
||||
alert("登录失败:" + e.message)
|
||||
}
|
||||
})
|
||||
|
||||
$("#login_def").click(function () {
|
||||
$("#pwd1").val("12345678");
|
||||
$("#login").click()
|
||||
})
|
||||
|
||||
|
||||
$("#btn_nameplate_clear").click(function () {
|
||||
$("#manufactor").val("");
|
||||
$("#system").val("");
|
||||
$("#customer").val("");
|
||||
})
|
||||
|
||||
$("#btn_read").click(function () {
|
||||
|
||||
var filepath = $("#filepath").val()
|
||||
var idx = filepath.lastIndexOf("\\")
|
||||
var folder = filepath.substr(0, idx)
|
||||
var file = filepath.substr(idx + 1)
|
||||
var txt = window.UKey.readFile(folder, file);
|
||||
$("#ta_txt").text(JSON.stringify(txt, null, 4))
|
||||
})
|
||||
|
||||
$("#btn_write").click(function () {
|
||||
alert("暂不开放")
|
||||
})
|
||||
|
||||
$("#btn_nameplate_tmp_load").click(function () {
|
||||
var def = {
|
||||
manufactor: "sunyard",
|
||||
system: "hsm",
|
||||
customer: "ICBC"
|
||||
}
|
||||
$("#manufactor").val(def.manufactor);
|
||||
$("#system").val(def.system);
|
||||
$("#customer").val(def.customer);
|
||||
})
|
||||
|
||||
$("#btn_nameplate_read").click(function () {
|
||||
|
||||
try {
|
||||
var txt = window.UKey.catRelease();
|
||||
var def = Object.assign({
|
||||
manufactor: "",
|
||||
system: "",
|
||||
customer: ""
|
||||
}, txt)
|
||||
|
||||
$("#manufactor").val(def.manufactor);
|
||||
$("#system").val(def.system);
|
||||
$("#customer").val(def.customer);
|
||||
|
||||
success("返显成功")
|
||||
} catch (e) {
|
||||
alert("返显失败:" + e.message)
|
||||
}
|
||||
})
|
||||
|
||||
|
||||
$("#btn_nameplate_tmp_load").click(function () {
|
||||
|
||||
|
||||
var json = localStorage.getItem("tmp")
|
||||
var def = {
|
||||
manufactor: "sunyard",
|
||||
system: "hsm",
|
||||
customer: "ICBC"
|
||||
}
|
||||
try {
|
||||
def = JSON.parse(json)
|
||||
} catch (e) {
|
||||
|
||||
}
|
||||
|
||||
$("#manufactor").val(def.manufactor);
|
||||
$("#system").val(def.system);
|
||||
$("#customer").val(def.customer);
|
||||
})
|
||||
|
||||
|
||||
$("#btn_nameplate_tmp_save").click(function () {
|
||||
var def = {
|
||||
manufactor: $("#manufactor").val(),
|
||||
system: $("#system").val(),
|
||||
customer: $("#customer").val()
|
||||
}
|
||||
|
||||
localStorage.setItem("tmp", JSON.stringify(def))
|
||||
|
||||
})
|
||||
|
||||
$("#btn_nameplate_release").click(function () {
|
||||
var def = {
|
||||
manufactor: $("#manufactor").val(),
|
||||
system: $("#system").val(),
|
||||
customer: $("#customer").val()
|
||||
}
|
||||
|
||||
check(def.manufactor, /\w+/, "厂家标记填写错误")
|
||||
check(def.system, /\w+/, "系统信息填写错误")
|
||||
check(def.customer, /\w+/, "客户信息填写错误")
|
||||
|
||||
try {
|
||||
window.UKey.release(def)
|
||||
success("发行成功")
|
||||
} catch (e) {
|
||||
alert("发行失败:" + e.message)
|
||||
}
|
||||
|
||||
})
|
||||
|
||||
|
||||
$("#reset").click(function () {
|
||||
alert("暂不开放")
|
||||
})
|
||||
$("#update1").click(function () {
|
||||
alert("暂不开放")
|
||||
})
|
||||
$("#update2").click(function () {
|
||||
alert("暂不开放")
|
||||
})
|
||||
|
||||
})
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
Vendored
+4
File diff suppressed because one or more lines are too long
Vendored
+1
File diff suppressed because one or more lines are too long
Vendored
+5
File diff suppressed because one or more lines are too long
@@ -0,0 +1,55 @@
|
||||
.tabs {
|
||||
overflow: hidden;
|
||||
width: 100%;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
.tabs li {
|
||||
float: left;
|
||||
margin: 0 -15px 0 0;
|
||||
}
|
||||
|
||||
.tabs a {
|
||||
float: left;
|
||||
position: relative;
|
||||
padding: 0 40px;
|
||||
height: 0;
|
||||
line-height: 30px;
|
||||
text-transform: uppercase;
|
||||
text-decoration: none;
|
||||
color: #fff;
|
||||
border-right: 30px solid transparent;
|
||||
border-bottom: 30px solid var(--mainColor);
|
||||
/*border-bottom-color: #777 \9;*/
|
||||
opacity: .3;
|
||||
filter: alpha(opacity=30);
|
||||
}
|
||||
|
||||
.tabs a:hover {
|
||||
border-bottom-color: var(--mainColor);
|
||||
opacity: 0.5;
|
||||
filter: alpha(opacity=50);
|
||||
}
|
||||
|
||||
.tabs a:focus {
|
||||
outline: 0;
|
||||
}
|
||||
|
||||
.tabs .current {
|
||||
z-index: 3;
|
||||
border-bottom-color: var(--mainColor);
|
||||
opacity: 1;
|
||||
filter: alpha(opacity=100);
|
||||
}
|
||||
|
||||
.tabs-content {
|
||||
background: #fff;
|
||||
border-top: 2px solid var(--mainColor);
|
||||
padding: 1rem 0;
|
||||
}
|
||||
|
||||
.tabs-content h2, #content h3, #content p {
|
||||
margin: 0 0 15px 0;
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
$(function (){
|
||||
|
||||
var $e = $(".tabs a").first();
|
||||
$e.addClass("current")
|
||||
showHideBlock( $e )
|
||||
|
||||
function showHideBlock($e){
|
||||
$(".tabs-content .tab").hide()
|
||||
var block = ".tabs-content .tab" + "." + $e.attr("name")
|
||||
$(block).show()
|
||||
}
|
||||
|
||||
|
||||
$(".tabs a").click(function (){
|
||||
$(".tabs a").removeClass("current")
|
||||
$(this).addClass("current")
|
||||
showHideBlock( $(this) )
|
||||
})
|
||||
})
|
||||
@@ -0,0 +1,45 @@
|
||||
// 覆盖默认行为
|
||||
function success(msg){
|
||||
layx.notice({
|
||||
title: '成功',
|
||||
type: 'success',
|
||||
message: msg
|
||||
});
|
||||
}
|
||||
|
||||
// 覆盖默认行为
|
||||
function warning(msg){
|
||||
layx.notice({
|
||||
title: '警告',
|
||||
type: 'warning',
|
||||
message: msg
|
||||
});
|
||||
}
|
||||
|
||||
// 覆盖默认行为
|
||||
function alert(msg){
|
||||
layx.notice({
|
||||
title: '错误',
|
||||
type: 'error',
|
||||
message: msg
|
||||
});
|
||||
}
|
||||
|
||||
function check(v, re, msg) {
|
||||
if (!re.test(v)) {
|
||||
alert("参数校验失败:" + msg)
|
||||
throw "参数校验失败"
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
function getyyyyMMdd(){
|
||||
var d = new Date();
|
||||
var curr_date = d.getDate();
|
||||
var curr_month = d.getMonth() + 1;
|
||||
var curr_year = d.getFullYear();
|
||||
String(curr_month).length < 2 ? (curr_month = "0" + curr_month): curr_month;
|
||||
String(curr_date).length < 2 ? (curr_date = "0" + curr_date): curr_date;
|
||||
var yyyyMMdd = curr_year + "" + curr_month +""+ curr_date;
|
||||
return yyyyMMdd;
|
||||
}
|
||||
@@ -0,0 +1,91 @@
|
||||
<!doctype html>
|
||||
<html lang="en" class="light-theme">
|
||||
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>JavaScript Event KeyCodes</title>
|
||||
<link rel="preconnect" href="https://fonts.gstatic.com/" crossorigin>
|
||||
<link href='https://fonts.googleapis.com/css?family=Montserrat' rel='stylesheet' type='text/css'>
|
||||
<meta name="viewport" content="width=device-width, user-scalable=no">
|
||||
<meta name="twitter:card" content="summary_large_image">
|
||||
<meta name="twitter:title" content="JavaScript Event KeyCodes">
|
||||
<meta name="twitter:description" content="Keycode testing tool - which keys map to which keycodes?">
|
||||
<meta name="twitter:creator" content="@wesbos">
|
||||
<meta name="twitter:image" content="https://cdn1.imggmi.com/uploads/2019/7/12/f6b03f5628f7850649714200ab517a52-full.png">
|
||||
<link rel="stylesheet" href="style.css?v=07232021">
|
||||
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/noty/3.1.4/noty.min.css" />
|
||||
<link rel="icon" href="">
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<script async src="//cdn.carbonads.com/carbon.js?serve=CESIK23L&placement=keycodeinfo" id="_carbonads_js"></script>
|
||||
<canvas width="128" height="128" hidden></canvas>
|
||||
<div class="display">
|
||||
<table class="table hide">
|
||||
<thead>
|
||||
<tr>
|
||||
<th>Key Code</th>
|
||||
<th>Key</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody class="table-body">
|
||||
</tbody>
|
||||
</table>
|
||||
<div class="wrap" aria-live="polite" aria-atomic="true">
|
||||
<p class="keycode-display"></p>
|
||||
<p class="text-display">Press any key to get the JavaScript event keycode</p>
|
||||
<div class="cards hide">
|
||||
<div class="card item-key">
|
||||
<div class="card-header">event.key</div>
|
||||
<div class="card-main">
|
||||
<div class="main-description">key</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="card item-location">
|
||||
<div class="card-header">event.location
|
||||
<a href="https://developer.mozilla.org/en-US/docs/Web/API/KeyboardEvent/location" target="_blank" rel="noopener"
|
||||
class="more-info"></a>
|
||||
</div>
|
||||
<div class="card-main">
|
||||
<div class="main-description">location</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="card item-which">
|
||||
<div class="card-header">
|
||||
event.which
|
||||
<a href="https://developer.mozilla.org/en-US/docs/Web/API/KeyboardEvent" target="_blank" rel="noopener"
|
||||
class="deprecated-link">(deprecated)</a>
|
||||
</div>
|
||||
<div class="card-main">
|
||||
<div class="main-description">which</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="card item-code">
|
||||
<div class="card-header">event.code</div>
|
||||
<div class="card-main">
|
||||
<div class="main-description">code</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="mobile-input">
|
||||
</div>
|
||||
</div>
|
||||
<div class="fixed-buttons">
|
||||
<button id="table-button" onclick={toggleTable()} class="toggle-button">Table</button>
|
||||
<button id="theme-button" onclick={toggleTheme()} class="toggle-button">Dark theme</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
<script type='text/javascript'>
|
||||
if ('serviceWorker' in navigator) {
|
||||
navigator.serviceWorker.register('./service-worker.js');
|
||||
}
|
||||
</script>
|
||||
<script src="https://cdnjs.cloudflare.com/ajax/libs/noty/3.1.4/noty.min.js"></script>
|
||||
<script src="scripts.js?v=07232021"></script>
|
||||
<script>!function (d, s, id) { var js, fjs = d.getElementsByTagName(s)[0], p = /^http:/.test(d.location) ? 'http' : 'https'; if (!d.getElementById(id)) { js = d.createElement(s); js.id = id; js.src = p + '://platform.twitter.com/widgets.js'; fjs.parentNode.insertBefore(js, fjs); } }(document, 'script', 'twitter-wjs');</script>
|
||||
<script defer src='https://static.cloudflareinsights.com/beacon.min.js' data-cf-beacon='{"token": "b45decb6c8304abfaafe7d19167b59b5"}'></script>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
@@ -0,0 +1,456 @@
|
||||
// #region Declare Variables
|
||||
|
||||
const keyCodes = {
|
||||
0: 'That key has no keycode',
|
||||
3: 'break',
|
||||
8: 'backspace / delete',
|
||||
9: 'tab',
|
||||
12: 'clear',
|
||||
13: 'enter',
|
||||
16: 'shift',
|
||||
17: 'ctrl',
|
||||
18: 'alt',
|
||||
19: 'pause/break',
|
||||
20: 'caps lock',
|
||||
21: 'hangul',
|
||||
25: 'hanja',
|
||||
27: 'escape',
|
||||
28: 'conversion',
|
||||
29: 'non-conversion',
|
||||
32: 'spacebar',
|
||||
33: 'page up',
|
||||
34: 'page down',
|
||||
35: 'end',
|
||||
36: 'home',
|
||||
37: 'left arrow',
|
||||
38: 'up arrow',
|
||||
39: 'right arrow',
|
||||
40: 'down arrow',
|
||||
41: 'select',
|
||||
42: 'print',
|
||||
43: 'execute',
|
||||
44: 'Print Screen',
|
||||
45: 'insert',
|
||||
46: 'delete',
|
||||
47: 'help',
|
||||
48: '0',
|
||||
49: '1',
|
||||
50: '2',
|
||||
51: '3',
|
||||
52: '4',
|
||||
53: '5',
|
||||
54: '6',
|
||||
55: '7',
|
||||
56: '8',
|
||||
57: '9',
|
||||
58: ':',
|
||||
59: 'semicolon (firefox), equals',
|
||||
60: '<',
|
||||
61: 'equals (firefox)',
|
||||
63: 'ß',
|
||||
64: '@ (firefox)',
|
||||
65: 'a',
|
||||
66: 'b',
|
||||
67: 'c',
|
||||
68: 'd',
|
||||
69: 'e',
|
||||
70: 'f',
|
||||
71: 'g',
|
||||
72: 'h',
|
||||
73: 'i',
|
||||
74: 'j',
|
||||
75: 'k',
|
||||
76: 'l',
|
||||
77: 'm',
|
||||
78: 'n',
|
||||
79: 'o',
|
||||
80: 'p',
|
||||
81: 'q',
|
||||
82: 'r',
|
||||
83: 's',
|
||||
84: 't',
|
||||
85: 'u',
|
||||
86: 'v',
|
||||
87: 'w',
|
||||
88: 'x',
|
||||
89: 'y',
|
||||
90: 'z',
|
||||
91: 'Windows Key / Left ⌘ / Chromebook Search key',
|
||||
92: 'right window key',
|
||||
93: 'Windows Menu / Right ⌘',
|
||||
95: 'sleep',
|
||||
96: 'numpad 0',
|
||||
97: 'numpad 1',
|
||||
98: 'numpad 2',
|
||||
99: 'numpad 3',
|
||||
100: 'numpad 4',
|
||||
101: 'numpad 5',
|
||||
102: 'numpad 6',
|
||||
103: 'numpad 7',
|
||||
104: 'numpad 8',
|
||||
105: 'numpad 9',
|
||||
106: 'multiply',
|
||||
107: 'add',
|
||||
108: 'numpad period (firefox)',
|
||||
109: 'subtract',
|
||||
110: 'decimal point',
|
||||
111: 'divide',
|
||||
112: 'f1',
|
||||
113: 'f2',
|
||||
114: 'f3',
|
||||
115: 'f4',
|
||||
116: 'f5',
|
||||
117: 'f6',
|
||||
118: 'f7',
|
||||
119: 'f8',
|
||||
120: 'f9',
|
||||
121: 'f10',
|
||||
122: 'f11',
|
||||
123: 'f12',
|
||||
124: 'f13',
|
||||
125: 'f14',
|
||||
126: 'f15',
|
||||
127: 'f16',
|
||||
128: 'f17',
|
||||
129: 'f18',
|
||||
130: 'f19',
|
||||
131: 'f20',
|
||||
132: 'f21',
|
||||
133: 'f22',
|
||||
134: 'f23',
|
||||
135: 'f24',
|
||||
136: 'f25',
|
||||
137: 'f26',
|
||||
138: 'f27',
|
||||
139: 'f28',
|
||||
140: 'f29',
|
||||
141: 'f30',
|
||||
142: 'f31',
|
||||
143: 'f32',
|
||||
144: 'num lock',
|
||||
145: 'scroll lock',
|
||||
151: 'airplane mode',
|
||||
160: '^',
|
||||
161: '!',
|
||||
162: '؛ (arabic semicolon)',
|
||||
163: '#',
|
||||
164: '$',
|
||||
165: 'ù',
|
||||
166: 'page backward',
|
||||
167: 'page forward',
|
||||
168: 'refresh',
|
||||
169: 'closing paren (AZERTY)',
|
||||
170: '*',
|
||||
171: '~ + * key',
|
||||
172: 'home key',
|
||||
173: 'minus (firefox), mute/unmute',
|
||||
174: 'decrease volume level',
|
||||
175: 'increase volume level',
|
||||
176: 'next',
|
||||
177: 'previous',
|
||||
178: 'stop',
|
||||
179: 'play/pause',
|
||||
180: 'e-mail',
|
||||
181: 'mute/unmute (firefox)',
|
||||
182: 'decrease volume level (firefox)',
|
||||
183: 'increase volume level (firefox)',
|
||||
186: 'semi-colon / ñ',
|
||||
187: 'equal sign',
|
||||
188: 'comma',
|
||||
189: 'dash',
|
||||
190: 'period',
|
||||
191: 'forward slash / ç',
|
||||
192: 'grave accent / ñ / æ / ö',
|
||||
193: '?, / or °',
|
||||
194: 'numpad period (chrome)',
|
||||
219: 'open bracket',
|
||||
220: 'back slash',
|
||||
221: 'close bracket / å',
|
||||
222: 'single quote / ø / ä',
|
||||
223: '`',
|
||||
224: 'left or right ⌘ key (firefox)',
|
||||
225: 'altgr',
|
||||
226: '< /git >, left back slash',
|
||||
230: 'GNOME Compose Key',
|
||||
231: 'ç',
|
||||
233: 'XF86Forward',
|
||||
234: 'XF86Back',
|
||||
235: 'non-conversion',
|
||||
240: 'alphanumeric',
|
||||
242: 'hiragana/katakana',
|
||||
243: 'half-width/full-width',
|
||||
244: 'kanji',
|
||||
251: 'unlock trackpad (Chrome/Edge)',
|
||||
255: 'toggle touchpad',
|
||||
};
|
||||
|
||||
const keyLocations = {
|
||||
0: 'General keys',
|
||||
1: 'Left-side modifier keys',
|
||||
2: 'Right-side modifier keys',
|
||||
3: 'Numpad',
|
||||
};
|
||||
|
||||
const spaceDescription = '(Space character)';
|
||||
|
||||
const body = document.querySelector('body');
|
||||
const mobileInputDiv = document.querySelector('.mobile-input');
|
||||
const canvas = document.querySelector('canvas');
|
||||
const ctx = canvas.getContext('2d');
|
||||
ctx.textBaseline = 'middle';
|
||||
ctx.textAlign = 'center';
|
||||
ctx.font = '110px sans-serif';
|
||||
|
||||
let theme = 'dark';
|
||||
|
||||
// #endregion
|
||||
|
||||
// #region Main Methods
|
||||
|
||||
function createTable() {
|
||||
const tableBody = document.querySelector('.table-body');
|
||||
for (const key in keyCodes) {
|
||||
const row = document.createElement('tr');
|
||||
row.innerHTML += `<td>${key}</td>`;
|
||||
row.innerHTML += `<td>${keyCodes[key]}</td>`;
|
||||
tableBody.appendChild(row);
|
||||
}
|
||||
}
|
||||
|
||||
function toggleTable() {
|
||||
const table = document.querySelector('.table');
|
||||
|
||||
// Toggle main content and table
|
||||
document.querySelector('.wrap').classList.toggle('hide');
|
||||
document.querySelector('.keycode-display').classList.toggle('hide');
|
||||
table.classList.toggle('hide');
|
||||
|
||||
// If hidden, show back arrow
|
||||
const hidden = table.classList.contains('hide');
|
||||
document.querySelector('#table-button').textContent = hidden ? 'Table' : '⬅';
|
||||
}
|
||||
|
||||
function drawNumberToCanvas(number) {
|
||||
ctx.clearRect(0, 0, canvas.width, canvas.height);
|
||||
ctx.fillStyle = 'black';
|
||||
ctx.fillText(number, canvas.width / 2, canvas.height / 2, canvas.width);
|
||||
const data = canvas.toDataURL('image/png');
|
||||
|
||||
const link = document.querySelector("link[rel*='icon']");
|
||||
link.type = 'image/x-icon';
|
||||
link.href = data;
|
||||
}
|
||||
|
||||
function createNotification(text) {
|
||||
// eslint-disable-next-line no-undef
|
||||
new Noty({
|
||||
type: 'info',
|
||||
layout: 'topLeft',
|
||||
timeout: '1500',
|
||||
theme: 'metroui',
|
||||
progressBar: false,
|
||||
text,
|
||||
}).show();
|
||||
}
|
||||
|
||||
function createTextarea(text) {
|
||||
const textArea = document.createElement('textarea');
|
||||
|
||||
// Place in top-left corner of screen regardless of scroll position.
|
||||
textArea.style.position = 'fixed';
|
||||
textArea.style.top = 0;
|
||||
textArea.style.left = 0;
|
||||
textArea.style.width = '2em';
|
||||
textArea.style.height = '2em';
|
||||
|
||||
textArea.style.padding = 0;
|
||||
|
||||
// Clean up any borders.
|
||||
textArea.style.border = 'none';
|
||||
textArea.style.outline = 'none';
|
||||
textArea.style.boxShadow = 'none';
|
||||
|
||||
// Avoid flash of white box if rendered for any reason.
|
||||
textArea.style.background = 'transparent';
|
||||
|
||||
textArea.value = text;
|
||||
|
||||
document.body.appendChild(textArea);
|
||||
return textArea;
|
||||
}
|
||||
|
||||
/**
|
||||
* This function is used to copy a string to clipboard
|
||||
* @param {string} text
|
||||
*/
|
||||
function copyTextToClipboard(text) {
|
||||
if (window.clipboardData && window.clipboardData.setData) {
|
||||
// IE specific code path to prevent textarea being shown while dialog is visible.
|
||||
return window.clipboardData.setData('Text', text);
|
||||
} else if (document.queryCommandSupported && document.queryCommandSupported('copy')) {
|
||||
const textArea = createTextarea(text);
|
||||
textArea.focus();
|
||||
textArea.select();
|
||||
|
||||
try {
|
||||
const status = document.execCommand('copy'); // Security exception may be thrown by some browsers.
|
||||
if (status) {
|
||||
createNotification('Copied text to clipboard');
|
||||
}
|
||||
return status;
|
||||
} catch (ex) {
|
||||
console.warn('Copy to clipboard failed.', ex);
|
||||
return false;
|
||||
} finally {
|
||||
document.body.removeChild(textArea);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// #endregion
|
||||
|
||||
// #region Event Listeners
|
||||
|
||||
document.addEventListener('touchstart', e => {
|
||||
if (document.querySelector('.mobile-input input') !== null) return;
|
||||
if (e.target.tagName === 'BUTTON') return;
|
||||
|
||||
const input = document.createElement('input');
|
||||
input.setAttribute('type', 'text');
|
||||
mobileInputDiv.appendChild(input);
|
||||
|
||||
// For some reason, the focus is immediately lost unless there is a delay on setting the focus
|
||||
setTimeout(() => {
|
||||
input.focus();
|
||||
}, 100);
|
||||
});
|
||||
|
||||
body.onkeydown = function(e) {
|
||||
if (!e.metaKey) {
|
||||
e.preventDefault();
|
||||
}
|
||||
drawNumberToCanvas(e.keyCode);
|
||||
|
||||
// Main e.keyCode display
|
||||
document.querySelector('.keycode-display').innerHTML = e.keyCode;
|
||||
|
||||
// Show the cards with all
|
||||
const cards = document.querySelector('.cards');
|
||||
cards.classList.add('active');
|
||||
cards.classList.remove('hide');
|
||||
document.querySelector('.text-display').classList.add('hide');
|
||||
|
||||
// Check if Key_Values is Unidentified then redirect to docs
|
||||
let newKeyText = '';
|
||||
if (e.key != null && e.key === 'Unidentified') {
|
||||
newKeyText = '<a href="https://developer.mozilla.org/en-US/docs/Web/API/KeyboardEvent/key/Key_Values#Special_values" target="_blank" rel="noopener">Unidentified</a>';
|
||||
} else if (e.key === ' ') {
|
||||
newKeyText = `<span class="text-muted">${spaceDescription}</span>`;
|
||||
} else {
|
||||
newKeyText = e.key || '';
|
||||
}
|
||||
|
||||
// Check if location is Unidentified then redirect to docs
|
||||
let newLocationText = '';
|
||||
let newLocationFriendlyText = '';
|
||||
if (e.location == null) {
|
||||
newLocationFriendlyText = 'Unknown';
|
||||
} else if (!(e.location in keyLocations)) {
|
||||
newLocationFriendlyText = '<a href="https://developer.mozilla.org/en-US/docs/Web/API/KeyboardEvent/location" target="_blank" rel="noopener">Other</a>';
|
||||
} else {
|
||||
newLocationFriendlyText = keyLocations[e.location];
|
||||
}
|
||||
|
||||
if (newLocationFriendlyText !== 'Unknown') {
|
||||
newLocationText = `${e.location} <span class="text-muted">(${newLocationFriendlyText})</span>`;
|
||||
} else {
|
||||
newLocationText = newLocationFriendlyText;
|
||||
}
|
||||
|
||||
// Check if code is Unidentified then redirect to docs
|
||||
let newCodeText = '';
|
||||
if (e.code != null && e.code === 'Unidentified') {
|
||||
newCodeText = '<a href="https://w3c.github.io/uievents-code/#table-key-code-special" target="_blank" rel="noopener">Unidentified</a>';
|
||||
} else {
|
||||
newCodeText = e.code || '';
|
||||
}
|
||||
|
||||
// Clear input if manually entered
|
||||
const mobileInput = document.querySelector('.mobile-input input');
|
||||
if (mobileInput !== null) {
|
||||
mobileInput.value = '';
|
||||
}
|
||||
|
||||
document.querySelector('.item-key .main-description').innerHTML = newKeyText;
|
||||
document.querySelector('.item-location .main-description').innerHTML = newLocationText;
|
||||
document.querySelector('.item-which .main-description').innerHTML = e.which || '';
|
||||
document.querySelector('.item-code .main-description').innerHTML = newCodeText;
|
||||
};
|
||||
|
||||
body.onkeyup = function(e) {
|
||||
if(e.keyCode == '44') {
|
||||
body.onkeydown(e);
|
||||
}
|
||||
}
|
||||
|
||||
const cardDivs = document.querySelectorAll('.card');
|
||||
Array.from(cardDivs).forEach(card => {
|
||||
card.addEventListener('click', onCardClick);
|
||||
});
|
||||
|
||||
function onCardClick() {
|
||||
const card = this;
|
||||
let description = card.querySelector('.card-main .main-description').innerHTML;
|
||||
description = description.replace(/<[^>]*>?/gm, '');
|
||||
if (description === spaceDescription) {
|
||||
description = ' ';
|
||||
}
|
||||
copyTextToClipboard(description);
|
||||
}
|
||||
|
||||
// #endregion
|
||||
|
||||
// #region Theme Methods
|
||||
|
||||
function queryMediaTheme() {
|
||||
window.matchMedia('(prefers-color-scheme: dark)').addEventListener('change', e => {
|
||||
theme = e.matches ? 'dark' : 'light';
|
||||
updateTheme();
|
||||
});
|
||||
if (window.matchMedia('(prefers-color-scheme: dark)').matches) {
|
||||
theme = 'dark';
|
||||
} else {
|
||||
theme = 'light';
|
||||
}
|
||||
}
|
||||
|
||||
function toggleTheme() {
|
||||
theme = (theme === 'light') ? 'dark' : 'light';
|
||||
updateTheme();
|
||||
}
|
||||
|
||||
function updateTheme() {
|
||||
const html = document.querySelector("html");
|
||||
const button = document.querySelector("#theme-button");
|
||||
|
||||
if (theme === 'light') {
|
||||
html.classList.add('light-theme');
|
||||
html.classList.remove('dark-theme');
|
||||
button.innerHTML = 'Dark theme';
|
||||
} else {
|
||||
html.classList.add('dark-theme');
|
||||
html.classList.remove('light-theme');
|
||||
button.innerHTML = 'Light theme';
|
||||
}
|
||||
}
|
||||
|
||||
// #endregion
|
||||
|
||||
// #region Init Methods
|
||||
|
||||
queryMediaTheme();
|
||||
updateTheme();
|
||||
createTable();
|
||||
drawNumberToCanvas('⌨️');
|
||||
|
||||
// #endregion
|
||||
@@ -0,0 +1,44 @@
|
||||
/**
|
||||
* The name of the current cache
|
||||
* @type {String}
|
||||
*/
|
||||
const CACHE_NAME = 'v6';
|
||||
|
||||
/**
|
||||
* Files to cache
|
||||
* @type {Array}
|
||||
*/
|
||||
const fileCache = [
|
||||
'/',
|
||||
'/index.html',
|
||||
'/scripts.js',
|
||||
'/style.css'
|
||||
];
|
||||
|
||||
this.oninstall = event => {
|
||||
event.waitUntil(
|
||||
caches.open(CACHE_NAME)
|
||||
.then(cache => cache.addAll(fileCache))
|
||||
);
|
||||
};
|
||||
|
||||
this.onfetch = event => {
|
||||
event.respondWith(
|
||||
caches.match(event.request)
|
||||
.then(response => {
|
||||
if (response) {
|
||||
return response;
|
||||
}
|
||||
|
||||
return fetch(event.request)
|
||||
.then(res => {
|
||||
const r = res.clone();
|
||||
caches.open(CACHE_NAME)
|
||||
.then(cache => {
|
||||
cache.put(event.request, r);
|
||||
});
|
||||
return res; // Don't wait for the request to cache
|
||||
});
|
||||
})
|
||||
);
|
||||
};
|
||||
@@ -0,0 +1,439 @@
|
||||
/* Themes */
|
||||
.light-theme {
|
||||
--background: #f2f4f8;
|
||||
--primary: #b9e9ff;
|
||||
--primary-border: #a2e2ff;
|
||||
|
||||
--text: #424242;
|
||||
--love-text: #d12026;
|
||||
--muted-text: #ccc;
|
||||
--context-text: #6597b2;
|
||||
|
||||
--button: #0091d4;
|
||||
|
||||
--card-background: #fff;
|
||||
--card-hover: rgba(220, 233, 255, 0.48);
|
||||
--table-separator: #dee2e6;
|
||||
}
|
||||
|
||||
.dark-theme {
|
||||
--background: #424242;
|
||||
--primary: #5b60ff;
|
||||
--primary-border: #4347b6;
|
||||
|
||||
--text: #f2f4f8;
|
||||
--love-text: #00e4c6;
|
||||
--context-text: #8effb1;
|
||||
|
||||
--button: var(--primary);
|
||||
|
||||
--card-background: #5f5f5f;
|
||||
--card-hover: rgba(47, 47, 47, 0.76);
|
||||
--table-separator: #828282;
|
||||
}
|
||||
|
||||
/* Reset */
|
||||
* {
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
}
|
||||
|
||||
html,
|
||||
body {
|
||||
height: 100%;
|
||||
margin: 0;
|
||||
font-family: 'Montserrat', 'sans-serif';
|
||||
color: var(--text);
|
||||
overflow: hidden;
|
||||
background: var(--background);
|
||||
}
|
||||
.display {
|
||||
text-align: center;
|
||||
display: table;
|
||||
height: 100%;
|
||||
max-width: 1280px;
|
||||
width: 100%;
|
||||
margin: 0 auto;
|
||||
}
|
||||
.wrap {
|
||||
display: table-cell;
|
||||
vertical-align: middle;
|
||||
}
|
||||
p {
|
||||
font-size: 100px; /* For lamers who don't support viewport sizing */
|
||||
font-size: 40vmin;
|
||||
text-align: center;
|
||||
margin: 0;
|
||||
}
|
||||
p.text-display {
|
||||
display: inline-block;
|
||||
color: var(--text);
|
||||
font-size: 20px;
|
||||
text-decoration: none;
|
||||
text-align: center;
|
||||
margin: 20px auto;
|
||||
padding: 15px 20px;
|
||||
background: var(--card-background);
|
||||
border-radius: 5px;
|
||||
min-width: 24px;
|
||||
font-size: 26px;
|
||||
box-shadow: 0 14px 26px rgba(0, 0, 0, 0.04);
|
||||
}
|
||||
|
||||
span.love {
|
||||
display: block;
|
||||
position: absolute;
|
||||
bottom: 10px;
|
||||
width: 100%;
|
||||
text-align: center;
|
||||
}
|
||||
|
||||
span.love a {
|
||||
text-decoration: none;
|
||||
color: var(--love-text);
|
||||
}
|
||||
|
||||
.twitter-follow-toggle-button {
|
||||
vertical-align: text-bottom;
|
||||
}
|
||||
|
||||
.twitter-share-toggle-button {
|
||||
vertical-align: text-bottom;
|
||||
}
|
||||
|
||||
/*
|
||||
Added New Card layout Css
|
||||
*/
|
||||
.cards {
|
||||
display: flex;
|
||||
flex-direction: row;
|
||||
flex-wrap: wrap;
|
||||
justify-content: center;
|
||||
align-items: baseline;
|
||||
margin-bottom: 20px;
|
||||
}
|
||||
.card {
|
||||
background: var(--card-background);
|
||||
border-radius: 5px;
|
||||
overflow: hidden;
|
||||
margin: 10px;
|
||||
flex: 1;
|
||||
max-width: calc(25% - 20px);
|
||||
box-shadow: 0 14px 26px rgba(0, 0, 0, 0.04);
|
||||
transition: all 0.3s ease-out;
|
||||
text-decoration: none;
|
||||
border: 1px solid rgba(0, 0, 0, 0.11);
|
||||
}
|
||||
|
||||
.item-location .card-main {
|
||||
padding: 9.5px;
|
||||
}
|
||||
|
||||
.item-location .main-description {
|
||||
font-size: 23px;
|
||||
}
|
||||
|
||||
.item-location .main-description span {
|
||||
display: block;
|
||||
}
|
||||
|
||||
.card:hover {
|
||||
cursor: pointer;
|
||||
transform: translateY(-5px) scale(1.005) translateZ(0);
|
||||
box-shadow: 0 24px 36px rgba(0, 0, 0, 0.11),
|
||||
0 24px 46px var(--card-hover);
|
||||
}
|
||||
|
||||
.card-header {
|
||||
text-align: center;
|
||||
font-size: 12px;
|
||||
font-weight: 600;
|
||||
border-bottom: 1px solid var(--primary-border);
|
||||
background-color: var(--primary);
|
||||
padding: 5px 10px;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
.more-info {
|
||||
height: 1.2em;
|
||||
width: 1.2em;
|
||||
float: right;
|
||||
}
|
||||
|
||||
.more-info::before {
|
||||
content: '(?)';
|
||||
color: var(--context-text);
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
.deprecated-link {
|
||||
position: absolute;
|
||||
top: 6px;
|
||||
right: 12px;
|
||||
color: var(--context-text);
|
||||
font-size: 10px;
|
||||
}
|
||||
|
||||
.card-main {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
padding: 15px 0;
|
||||
}
|
||||
|
||||
.main-description {
|
||||
font-size: 28px;
|
||||
text-align: center;
|
||||
min-height: 35px;
|
||||
}
|
||||
|
||||
.text-muted {
|
||||
font-size: 0.65em;
|
||||
color: var(--muted-text);
|
||||
}
|
||||
|
||||
.table {
|
||||
width: 50%;
|
||||
table-layout: fixed;
|
||||
margin: auto;
|
||||
margin-top: 5vh;
|
||||
box-shadow: 0 14px 26px rgba(0, 0, 0, 0.04);
|
||||
border-radius: 5px;
|
||||
border-collapse: collapse;
|
||||
}
|
||||
|
||||
.table-body {
|
||||
display: block;
|
||||
width: 100%;
|
||||
overflow: auto;
|
||||
height: 77vh;
|
||||
background: var(--card-background);
|
||||
}
|
||||
|
||||
.table thead tr {
|
||||
display: block;
|
||||
border-radius: 5px;
|
||||
}
|
||||
|
||||
.table thead {
|
||||
font-size: 12px;
|
||||
font-weight: 600;
|
||||
border-bottom: 1px solid var(--primary-border);
|
||||
background-color: var(--primary);
|
||||
}
|
||||
|
||||
.table th,
|
||||
.table td {
|
||||
padding: 0.3rem 1rem;
|
||||
text-align: left;
|
||||
min-width: 100px;
|
||||
font-size: 1.2rem;
|
||||
}
|
||||
|
||||
.table th {
|
||||
padding: 0.5rem 1rem;
|
||||
}
|
||||
.table td {
|
||||
border-bottom: 1px solid var(--table-separator);
|
||||
}
|
||||
.table tbody tr:hover {
|
||||
background-color: rgba(0, 0, 0, 0.075);
|
||||
}
|
||||
|
||||
.fixed-buttons {
|
||||
position: absolute;
|
||||
top: 15px;
|
||||
right: 15px;
|
||||
}
|
||||
|
||||
.fixed-buttons :nth-child(1) {
|
||||
margin-right: 15px;
|
||||
}
|
||||
|
||||
.toggle-button {
|
||||
font: bold 16px arial;
|
||||
color: var(--button);
|
||||
border: 2px solid var(--button);
|
||||
background: transparent;
|
||||
border-radius: 5px;
|
||||
padding: 5px 10px;
|
||||
transition: all 0.3s ease-out;
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
.toggle-button:hover {
|
||||
transform: translateY(-2px) scale(1.005) translateZ(0);
|
||||
box-shadow: 0 6px 10px rgba(0, 0, 0, 0.11),
|
||||
0 6px 9px var(--card-hover);
|
||||
}
|
||||
|
||||
.toggle-button:active {
|
||||
transform: translateY(2px) scale(0.995) translateZ(0);
|
||||
box-shadow: none;
|
||||
}
|
||||
|
||||
.mobile-input input {
|
||||
width: calc(100% - 20px);
|
||||
height: 4rem;
|
||||
margin: 10px;
|
||||
font-size: 4rem;
|
||||
border: 1px solid #dadada;
|
||||
border-radius: 4px;
|
||||
box-shadow: 0 14px 26px rgba(0, 0, 0, 0.04);
|
||||
transition: all 0.3s ease-out;
|
||||
}
|
||||
|
||||
.mobile-input input:focus {
|
||||
outline: none;
|
||||
transform: translateY(-5px) scale(1.005) translateZ(0);
|
||||
box-shadow: 0 24px 36px rgba(0, 0, 0, 0.11),
|
||||
0 24px 46px var(--card-hover);
|
||||
}
|
||||
|
||||
@media (min-width: 601px) and (max-width: 980px) {
|
||||
body {
|
||||
overflow-y: auto;
|
||||
}
|
||||
.card {
|
||||
flex: 45%;
|
||||
max-width: 45%;
|
||||
}
|
||||
.display {
|
||||
width: 80%;
|
||||
}
|
||||
.main-description {
|
||||
min-height: 34px;
|
||||
}
|
||||
}
|
||||
@media (max-width: 600px) {
|
||||
body {
|
||||
overflow-y: auto;
|
||||
}
|
||||
.card {
|
||||
flex: 100%;
|
||||
max-width: 100%;
|
||||
}
|
||||
.display {
|
||||
width: 90%;
|
||||
}
|
||||
.table {
|
||||
width: 100%;
|
||||
margin-top: 4rem;
|
||||
}
|
||||
.table-body {
|
||||
height: 60vh;
|
||||
}
|
||||
}
|
||||
|
||||
.hide {
|
||||
display: none !important;
|
||||
}
|
||||
.active {
|
||||
display: flex;
|
||||
}
|
||||
|
||||
|
||||
/* Carbon Ads */
|
||||
#carbonads * {
|
||||
margin: initial;
|
||||
padding: initial;
|
||||
}
|
||||
|
||||
#carbonads {
|
||||
display: flex;
|
||||
position: fixed;
|
||||
top: 1rem;
|
||||
left: 1rem;
|
||||
font-size: 11px;
|
||||
overflow: hidden;
|
||||
max-width: 130px;
|
||||
border-radius: 4px;
|
||||
box-shadow: 0 0 1px hsla(0, 0%, 0%, .15);
|
||||
}
|
||||
|
||||
#carbonads a {
|
||||
text-decoration: none;
|
||||
color: #111;
|
||||
}
|
||||
|
||||
#carbonads a:hover {
|
||||
color: #111;
|
||||
}
|
||||
|
||||
#carbonads .carbon-img {
|
||||
display: block;
|
||||
|
||||
line-height: 1;
|
||||
max-width: 130px;
|
||||
}
|
||||
|
||||
#carbonads .carbon-img img {
|
||||
display: block;
|
||||
margin: 0 auto;
|
||||
|
||||
width: 130px;
|
||||
height: 100px;
|
||||
}
|
||||
|
||||
#carbonads .carbon-text {
|
||||
display: block;
|
||||
padding: 8px 10px;
|
||||
|
||||
line-height: 1.35;
|
||||
text-align: left;
|
||||
background-color: hsl(0, 0%, 98%);
|
||||
}
|
||||
|
||||
#carbonads .carbon-poweredby {
|
||||
display: block;
|
||||
padding: 10px;
|
||||
|
||||
font-size: 8px;
|
||||
font-weight: 600;
|
||||
line-height: 0;
|
||||
letter-spacing: .5px;
|
||||
text-transform: uppercase;
|
||||
background: repeating-linear-gradient(-45deg,
|
||||
transparent,
|
||||
transparent 5px,
|
||||
hsla(0, 0%, 0%, .025) 5px,
|
||||
hsla(0, 0%, 0%, .025) 10px) hsla(203, 11%, 95%, .4);
|
||||
background-color: hsl(0, 0%, 98%);
|
||||
}
|
||||
|
||||
@media only screen and (min-width: 320px) and (max-width: 759px) {
|
||||
#carbonads {
|
||||
float: none;
|
||||
position: relative;
|
||||
margin: 4rem auto 0;
|
||||
|
||||
max-width: 330px;
|
||||
}
|
||||
|
||||
#carbonads .carbon-wrap {
|
||||
display: flex;
|
||||
|
||||
flex-direction: row;
|
||||
}
|
||||
|
||||
#carbonads .carbon-img {
|
||||
margin: 0;
|
||||
}
|
||||
|
||||
#carbonads .carbon-text {
|
||||
padding: 10px 10px 0 10px;
|
||||
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
#carbonads .carbon-poweredby {
|
||||
position: absolute;
|
||||
right: 0;
|
||||
bottom: 0;
|
||||
|
||||
text-align: center;
|
||||
border-radius: 0;
|
||||
border-top-left-radius: 3px;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,152 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<meta charset="UTF-8">
|
||||
<meta name="viewport" content="width=device-width,initial-scale=1,minimum-scale=1,maximum-scale=1,user-scalable=no" />
|
||||
<title>手写签名</title>
|
||||
<!--<link rel="stylesheet" href="css/style.css">-->
|
||||
<style>
|
||||
.canvasDiv {
|
||||
width: 800px;
|
||||
height: 500px;
|
||||
border: 1px solid gray;
|
||||
}
|
||||
|
||||
#editing_area {
|
||||
width: 800px;
|
||||
height: 500px;
|
||||
/*border: 1px solid darkred;*/
|
||||
}
|
||||
#canvasEdit {
|
||||
width: 800px;
|
||||
height: 500px;
|
||||
/*border: 1px solid gold;*/
|
||||
}
|
||||
|
||||
.btnDiv a {
|
||||
cursor: pointer;
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<div class="canvasDiv">
|
||||
|
||||
<div id="editing_area">
|
||||
<canvas id="canvasEdit"></canvas>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<span>身份证:</span>
|
||||
<span id="idcard"></span>
|
||||
</div>
|
||||
<div class="btnDiv">
|
||||
<a id="sign_clear" class="clearBtn">清除</a>
|
||||
<a id="sign_clear1" class="down none" download="download">下载</a>
|
||||
<a id="sign_clear2" class="clearBtn">截屏</a>
|
||||
</div>
|
||||
<script src="http://libs.baidu.com/jquery/2.0.0/jquery.min.js"></script>
|
||||
<script type="text/javascript" src="../vue/public/js/esign.js"></script>
|
||||
<script type="text/javascript" src="../vue/public/js/html2canvas.min.js"></script>
|
||||
<script type="text/javascript">
|
||||
|
||||
|
||||
function GetQueryString(name) {
|
||||
var reg = new RegExp("(^|&)" + name + "=([^&]*)(&|$)", "i");
|
||||
var r = window.location.search.substr(1).match(reg); //获取url中"?"符后的字符串并正则匹配
|
||||
var context = "";
|
||||
if (r != null)
|
||||
context = r[2];
|
||||
reg = null;
|
||||
r = null;
|
||||
return context == null || context == "" || context == "undefined" ? "" : context;
|
||||
}
|
||||
|
||||
function convertCanvasToImage(canvas) {
|
||||
return canvas.toDataURL("image/png");
|
||||
};
|
||||
|
||||
function checkIDCard(idcode){
|
||||
// 加权因子
|
||||
var weight_factor = [7,9,10,5,8,4,2,1,6,3,7,9,10,5,8,4,2];
|
||||
// 校验码
|
||||
var check_code = ['1', '0', 'X' , '9', '8', '7', '6', '5', '4', '3', '2'];
|
||||
|
||||
var code = idcode + "";
|
||||
var last = idcode[17];//最后一位
|
||||
|
||||
var seventeen = code.substring(0,17);
|
||||
|
||||
// ISO 7064:1983.MOD 11-2
|
||||
// 判断最后一位校验码是否正确
|
||||
var arr = seventeen.split("");
|
||||
var len = arr.length;
|
||||
var num = 0;
|
||||
for(var i = 0; i < len; i++){
|
||||
num = num + arr[i] * weight_factor[i];
|
||||
}
|
||||
|
||||
// 获取余数
|
||||
var resisue = num%11;
|
||||
var last_no = check_code[resisue];
|
||||
|
||||
// 格式的正则
|
||||
// 正则思路
|
||||
/*
|
||||
第一位不可能是0
|
||||
第二位到第六位可以是0-9
|
||||
第七位到第十位是年份,所以七八位为19或者20
|
||||
十一位和十二位是月份,这两位是01-12之间的数值
|
||||
十三位和十四位是日期,是从01-31之间的数值
|
||||
十五,十六,十七都是数字0-9
|
||||
十八位可能是数字0-9,也可能是X
|
||||
*/
|
||||
var idcard_patter = /^[1-9][0-9]{5}([1][9][0-9]{2}|[2][0][0|1][0-9])([0][1-9]|[1][0|1|2])([0][1-9]|[1|2][0-9]|[3][0|1])[0-9]{3}([0-9]|[X])$/;
|
||||
|
||||
// 判断格式是否正确
|
||||
var format = idcard_patter.test(idcode);
|
||||
|
||||
// 返回验证结果,校验码和格式同时正确才算是合法的身份证号码
|
||||
return last === last_no && format ? true : false;
|
||||
}
|
||||
|
||||
function closeWin() {
|
||||
try {
|
||||
window.opener = window;
|
||||
var win = window.open("", "_self");
|
||||
win.close();
|
||||
//frame的时候
|
||||
top.close();
|
||||
} catch (e) {
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
function takeScreenshot() {
|
||||
html2canvas(document.body, {
|
||||
width: document.body.clientWidth / 2 + 1,
|
||||
}).then(function(canvas) {
|
||||
alert('截取成功');
|
||||
var imgUrl = convertCanvasToImage(canvas); //截取图片路径,该路径为服务器参数
|
||||
console.log(imgUrl);
|
||||
document.querySelector(".down").setAttribute('href', imgUrl);
|
||||
$('#sign_clear1').removeClass('none');
|
||||
});
|
||||
};
|
||||
$(function() {
|
||||
|
||||
var idcard = GetQueryString("idcard")
|
||||
if ( ! idcard || ! checkIDCard(idcard)) {
|
||||
// alert("身份证号错误, 非法访问!")
|
||||
// closeWin()
|
||||
} else {
|
||||
|
||||
$("#idcard").text( idcard )
|
||||
|
||||
//初始化
|
||||
$(document).esign("canvasEdit", "sign_show", "sign_clear", "sign_ok");
|
||||
$(document).on('click', '#sign_clear2', takeScreenshot);
|
||||
}
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
+1611
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,370 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>U 盾维护工具</title>
|
||||
<style>
|
||||
:root {
|
||||
--mainColor: salmon;
|
||||
}
|
||||
|
||||
html, body {
|
||||
margin: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.title {
|
||||
color: var(--mainColor);
|
||||
}
|
||||
|
||||
.container {
|
||||
margin: 2rem auto;
|
||||
border: var(--mainColor) solid 2px;
|
||||
border-radius: 10px;
|
||||
width: 80%;
|
||||
height: 80%;
|
||||
text-align: left;
|
||||
}
|
||||
|
||||
.group {
|
||||
padding: 1rem;
|
||||
margin: 1rem;
|
||||
}
|
||||
|
||||
.form input {
|
||||
display: block;
|
||||
margin: 0.5rem 0;
|
||||
}
|
||||
|
||||
</style>
|
||||
<link rel="stylesheet" type="text/css" href="tabs.css">
|
||||
<link rel="stylesheet" type="text/css" href="layx.min.css">
|
||||
</head>
|
||||
<body>
|
||||
|
||||
<div style="width: 100%; text-align: center;">
|
||||
<h2 class="title">信雅达 UKey 发行工具</h2>
|
||||
</div>
|
||||
|
||||
<div class="container">
|
||||
|
||||
|
||||
<div class="group" style="width: 100%; ">
|
||||
<select id="ukeys" style="height: 1.5rem; width: 308px">
|
||||
</select>
|
||||
<button id="btn_refresh" style="margin-right: 1rem">刷  新</button>
|
||||
</div>
|
||||
|
||||
<div class="group" style="width: 100%;">
|
||||
<input id="pwd1" style="width: 300px;height: 1.06rem" type="password" maxlength="8" placeholder="口令,8 个数字">
|
||||
<button id="login" style="margin-right: 1rem">登  录</button>
|
||||
<button id="login_def" style="margin-right: 1rem">默认口令</button>
|
||||
</div>
|
||||
|
||||
<div class="group" style="height: 10rem">
|
||||
<ul class="tabs">
|
||||
<li>
|
||||
<a href="#" name="tab_public">UKey 发行</a>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<a href="#" name="tab_file">文件操作</a>
|
||||
</li>
|
||||
|
||||
<li>
|
||||
<a href="#" name="tab_pin">PIN 管理</a>
|
||||
</li>
|
||||
|
||||
|
||||
</ul>
|
||||
|
||||
<div class="tabs-content">
|
||||
|
||||
|
||||
<div class="tab tab_public">
|
||||
|
||||
<div class="form">
|
||||
|
||||
<input id="manufactor" style="width: 300px; height: 1.06rem" type="text" value=""
|
||||
placeholder="厂家标记">
|
||||
<input id="system" style="width: 300px; height: 1.06rem" type="text" value="" placeholder="系统信息">
|
||||
<input id="customer" style="width: 300px; height: 1.06rem" type="text" value="" placeholder="客户信息">
|
||||
|
||||
</div>
|
||||
|
||||
<div style="margin: 1rem 0 ">
|
||||
<button id="btn_nameplate_clear" style="margin-right: 1rem">清空</button>
|
||||
<button id="btn_nameplate_tmp_save" style="margin-right: 1rem">临存</button>
|
||||
<button id="btn_nameplate_tmp_load" style="margin-right: 1rem">临取</button>
|
||||
<button id="btn_nameplate_read" style="margin-right: 1rem">返显</button>
|
||||
</div>
|
||||
|
||||
<button id="btn_nameplate_release" style="margin-right: 1rem">发  行</button>
|
||||
|
||||
</div>
|
||||
|
||||
<div class="tab tab_file">
|
||||
|
||||
|
||||
<input id="path" style="width: 300px; height: 1.06rem" type="text" value="\root\mana"
|
||||
placeholder="文件目录">
|
||||
<button id="btn_list_path" style="margin-right: 1rem">枚  举</button>
|
||||
|
||||
<textarea id="ta_files" style="display: block; margin: 1rem 0; width: 375px; height: 100px;"
|
||||
readonly></textarea>
|
||||
|
||||
|
||||
<input id="filepath" style="width: 300px; height: 1.06rem" type="text" value="\root\mana\name"
|
||||
maxlength="6" placeholder="文件">
|
||||
<button id="btn_read" style="margin-right: 0.5rem">读</button>
|
||||
<button id="btn_write" style="margin-right: 1rem">写</button>
|
||||
|
||||
<textarea id="ta_txt" style="display: block; margin: 1rem 0; width: 375px; height: 100px;"
|
||||
readonly></textarea>
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
<div class="tab tab_pin">
|
||||
<div class="group" style="width: 100%; ">
|
||||
<input id="pwd2" style="width: 300px;height: 1.06rem" type="password" maxlength="8"
|
||||
placeholder="口令,8 个数字">
|
||||
<button id="login2" style="margin-right: 1rem">授  权</button>
|
||||
<button id="login_def2" style="margin-right: 1rem">默认口令</button>
|
||||
</div>
|
||||
|
||||
|
||||
<div class="form group">
|
||||
<input id="old_pwd" style="width: 360px;height: 1.06rem" type="password" maxlength="8"
|
||||
placeholder="旧口令,8 个数字">
|
||||
<input id="new_pwd1" style="width: 360px;height: 1.06rem" type="password" maxlength="8"
|
||||
placeholder="新口令,8 个数字">
|
||||
<input id="new_pwd2" style="width: 360px;height: 1.06rem" type="password" maxlength="8"
|
||||
placeholder="重复新口令,8 个数字">
|
||||
<button id="update1" style="margin-right: 1rem">修改操作员 PIN</button>
|
||||
<button id="update2" style="margin-right: 1rem">修改管理员 PIN</button>
|
||||
<button id="reset" style="margin-right: 1rem">解锁操作员 PIN</button>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
</div>
|
||||
|
||||
|
||||
<!-- UKey 支持, 共 3 个 js-->
|
||||
<!-- jquery -->
|
||||
<script type="text/javascript" src="./jquery.min.js"></script>
|
||||
<script type="text/javascript" src="./fiseckey.js"></script>
|
||||
<script type="text/javascript" src="./ukey.js"></script>
|
||||
|
||||
|
||||
<!-- 演示程序 -->
|
||||
<script type="text/javascript" src="./tabs.js"></script>
|
||||
<script type="application/javascript" src="layx.min.js"></script>
|
||||
<script type="application/javascript" src="tools.js"></script>
|
||||
<script type="application/javascript">
|
||||
$(function () {
|
||||
function refresh() {
|
||||
var list = window.UKey.enumDevByArray()
|
||||
if (list) {
|
||||
var ll = list.split("|");
|
||||
var options = ""
|
||||
for (var i = 0; i < ll.length; i++) {
|
||||
var value = ll[i].split(",")[0]
|
||||
options += "<option value =\"" + value + "\">" + ll[i] + "</option>"
|
||||
}
|
||||
$("#ukeys").html(options);
|
||||
}
|
||||
}
|
||||
|
||||
refresh();
|
||||
|
||||
$("#btn_refresh").click(function () {
|
||||
refresh()
|
||||
success("刷新成功")
|
||||
})
|
||||
|
||||
$("#btn_list_path").click(function () {
|
||||
var path = $("#path").val();
|
||||
try {
|
||||
var ret = window.UKey.enumDir(path)
|
||||
|
||||
var out = ""
|
||||
for (var i = 0; i < ret.folders.length; i++) {
|
||||
out += "文件夹:\t" + ret.folders[i] + "\r\n"
|
||||
}
|
||||
|
||||
for (var i = 0; i < ret.files.length; i++) {
|
||||
out += "文件:\t" + ret.files[i] + "\r\n"
|
||||
}
|
||||
|
||||
$("#ta_files").text(out)
|
||||
success("枚举成功")
|
||||
|
||||
} catch (e) {
|
||||
alert("枚举失败:" + e.message)
|
||||
}
|
||||
})
|
||||
|
||||
|
||||
$("#login2").click(function () {
|
||||
var pwd2 = $("#pwd2").val();
|
||||
check(pwd2, /\d{8}/, "口令输入错误")
|
||||
var ukey = $("#ukeys").val();
|
||||
|
||||
try {
|
||||
window.UKey.admin(ukey, pwd2)
|
||||
success("登录成功")
|
||||
} catch (e) {
|
||||
alert("登录失败:" + e.message)
|
||||
}
|
||||
})
|
||||
|
||||
$("#login2_def").click(function () {
|
||||
$("#pwd2").val("12345678");
|
||||
$("#login2").click()
|
||||
})
|
||||
|
||||
$("#login").click(function () {
|
||||
var pwd1 = $("#pwd1").val();
|
||||
check(pwd1, /\d{8}/, "口令输入错误")
|
||||
var ukey = $("#ukeys").val();
|
||||
|
||||
try {
|
||||
window.UKey.login(ukey, pwd1)
|
||||
success("登录成功")
|
||||
} catch (e) {
|
||||
alert("登录失败:" + e.message)
|
||||
}
|
||||
})
|
||||
|
||||
$("#login_def").click(function () {
|
||||
$("#pwd1").val("12345678");
|
||||
$("#login").click()
|
||||
})
|
||||
|
||||
|
||||
$("#btn_nameplate_clear").click(function () {
|
||||
$("#manufactor").val("");
|
||||
$("#system").val("");
|
||||
$("#customer").val("");
|
||||
})
|
||||
|
||||
$("#btn_read").click(function () {
|
||||
|
||||
var filepath = $("#filepath").val()
|
||||
var idx = filepath.lastIndexOf("\\")
|
||||
var folder = filepath.substr(0, idx)
|
||||
var file = filepath.substr(idx + 1)
|
||||
var txt = window.UKey.readFile(folder, file);
|
||||
$("#ta_txt").text(JSON.stringify(txt, null, 4))
|
||||
})
|
||||
|
||||
$("#btn_write").click(function () {
|
||||
alert("暂不开放")
|
||||
})
|
||||
|
||||
$("#btn_nameplate_tmp_load").click(function () {
|
||||
var def = {
|
||||
manufactor: "sunyard",
|
||||
system: "hsm",
|
||||
customer: "ICBC"
|
||||
}
|
||||
$("#manufactor").val(def.manufactor);
|
||||
$("#system").val(def.system);
|
||||
$("#customer").val(def.customer);
|
||||
})
|
||||
|
||||
$("#btn_nameplate_read").click(function () {
|
||||
|
||||
try {
|
||||
var txt = window.UKey.catRelease();
|
||||
var def = Object.assign({
|
||||
manufactor: "",
|
||||
system: "",
|
||||
customer: ""
|
||||
}, txt)
|
||||
|
||||
$("#manufactor").val(def.manufactor);
|
||||
$("#system").val(def.system);
|
||||
$("#customer").val(def.customer);
|
||||
|
||||
success("返显成功")
|
||||
} catch (e) {
|
||||
alert("返显失败:" + e.message)
|
||||
}
|
||||
})
|
||||
|
||||
|
||||
$("#btn_nameplate_tmp_load").click(function () {
|
||||
|
||||
|
||||
var json = localStorage.getItem("tmp")
|
||||
var def = {
|
||||
manufactor: "sunyard",
|
||||
system: "hsm",
|
||||
customer: "ICBC"
|
||||
}
|
||||
try {
|
||||
def = JSON.parse(json)
|
||||
} catch (e) {
|
||||
|
||||
}
|
||||
|
||||
$("#manufactor").val(def.manufactor);
|
||||
$("#system").val(def.system);
|
||||
$("#customer").val(def.customer);
|
||||
})
|
||||
|
||||
|
||||
$("#btn_nameplate_tmp_save").click(function () {
|
||||
var def = {
|
||||
manufactor: $("#manufactor").val(),
|
||||
system: $("#system").val(),
|
||||
customer: $("#customer").val()
|
||||
}
|
||||
|
||||
localStorage.setItem("tmp", JSON.stringify(def))
|
||||
|
||||
})
|
||||
|
||||
$("#btn_nameplate_release").click(function () {
|
||||
var def = {
|
||||
manufactor: $("#manufactor").val(),
|
||||
system: $("#system").val(),
|
||||
customer: $("#customer").val()
|
||||
}
|
||||
|
||||
check(def.manufactor, /\w+/, "厂家标记填写错误")
|
||||
check(def.system, /\w+/, "系统信息填写错误")
|
||||
check(def.customer, /\w+/, "客户信息填写错误")
|
||||
|
||||
try {
|
||||
window.UKey.release(def)
|
||||
success("发行成功")
|
||||
} catch (e) {
|
||||
alert("发行失败:" + e.message)
|
||||
}
|
||||
|
||||
})
|
||||
|
||||
|
||||
$("#reset").click(function () {
|
||||
alert("暂不开放")
|
||||
})
|
||||
$("#update1").click(function () {
|
||||
alert("暂不开放")
|
||||
})
|
||||
$("#update2").click(function () {
|
||||
alert("暂不开放")
|
||||
})
|
||||
|
||||
})
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
Vendored
+4
File diff suppressed because one or more lines are too long
Vendored
+1
File diff suppressed because one or more lines are too long
Vendored
+5
File diff suppressed because one or more lines are too long
@@ -0,0 +1,55 @@
|
||||
.tabs {
|
||||
overflow: hidden;
|
||||
width: 100%;
|
||||
margin: 0;
|
||||
padding: 0;
|
||||
list-style: none;
|
||||
}
|
||||
|
||||
.tabs li {
|
||||
float: left;
|
||||
margin: 0 -15px 0 0;
|
||||
}
|
||||
|
||||
.tabs a {
|
||||
float: left;
|
||||
position: relative;
|
||||
padding: 0 40px;
|
||||
height: 0;
|
||||
line-height: 30px;
|
||||
text-transform: uppercase;
|
||||
text-decoration: none;
|
||||
color: #fff;
|
||||
border-right: 30px solid transparent;
|
||||
border-bottom: 30px solid var(--mainColor);
|
||||
/*border-bottom-color: #777 \9;*/
|
||||
opacity: .3;
|
||||
filter: alpha(opacity=30);
|
||||
}
|
||||
|
||||
.tabs a:hover {
|
||||
border-bottom-color: var(--mainColor);
|
||||
opacity: 0.5;
|
||||
filter: alpha(opacity=50);
|
||||
}
|
||||
|
||||
.tabs a:focus {
|
||||
outline: 0;
|
||||
}
|
||||
|
||||
.tabs .current {
|
||||
z-index: 3;
|
||||
border-bottom-color: var(--mainColor);
|
||||
opacity: 1;
|
||||
filter: alpha(opacity=100);
|
||||
}
|
||||
|
||||
.tabs-content {
|
||||
background: #fff;
|
||||
border-top: 2px solid var(--mainColor);
|
||||
padding: 1rem 0;
|
||||
}
|
||||
|
||||
.tabs-content h2, #content h3, #content p {
|
||||
margin: 0 0 15px 0;
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
$(function (){
|
||||
|
||||
var $e = $(".tabs a").first();
|
||||
$e.addClass("current")
|
||||
showHideBlock( $e )
|
||||
|
||||
function showHideBlock($e){
|
||||
$(".tabs-content .tab").hide()
|
||||
var block = ".tabs-content .tab" + "." + $e.attr("name")
|
||||
$(block).show()
|
||||
}
|
||||
|
||||
|
||||
$(".tabs a").click(function (){
|
||||
$(".tabs a").removeClass("current")
|
||||
$(this).addClass("current")
|
||||
showHideBlock( $(this) )
|
||||
})
|
||||
})
|
||||
+1597
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,45 @@
|
||||
// 覆盖默认行为
|
||||
function success(msg){
|
||||
layx.notice({
|
||||
title: '成功',
|
||||
type: 'success',
|
||||
message: msg
|
||||
});
|
||||
}
|
||||
|
||||
// 覆盖默认行为
|
||||
function warning(msg){
|
||||
layx.notice({
|
||||
title: '警告',
|
||||
type: 'warning',
|
||||
message: msg
|
||||
});
|
||||
}
|
||||
|
||||
// 覆盖默认行为
|
||||
function alert(msg){
|
||||
layx.notice({
|
||||
title: '错误',
|
||||
type: 'error',
|
||||
message: msg
|
||||
});
|
||||
}
|
||||
|
||||
function check(v, re, msg) {
|
||||
if (!re.test(v)) {
|
||||
alert("参数校验失败:" + msg)
|
||||
throw "参数校验失败"
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
function getyyyyMMdd(){
|
||||
var d = new Date();
|
||||
var curr_date = d.getDate();
|
||||
var curr_month = d.getMonth() + 1;
|
||||
var curr_year = d.getFullYear();
|
||||
String(curr_month).length < 2 ? (curr_month = "0" + curr_month): curr_month;
|
||||
String(curr_date).length < 2 ? (curr_date = "0" + curr_date): curr_date;
|
||||
var yyyyMMdd = curr_year + "" + curr_month +""+ curr_date;
|
||||
return yyyyMMdd;
|
||||
}
|
||||
+274
@@ -0,0 +1,274 @@
|
||||
(function( root ){
|
||||
|
||||
var DIR = DIRR
|
||||
var FISECKEY = root.FISECKEY;
|
||||
var hDevice = undefined;
|
||||
|
||||
|
||||
if ( ! FISECKEY ) {
|
||||
console.error("缺少 FISECKEY 支持 !!!")
|
||||
}
|
||||
|
||||
function stringToHex(str){
|
||||
var val = "";
|
||||
for (var i = 0; i < str.length; i++) {
|
||||
if (val == "")
|
||||
val = str.charCodeAt(i).toString(16);
|
||||
else
|
||||
val += str.charCodeAt(i).toString(16);
|
||||
}
|
||||
val += ""
|
||||
return val
|
||||
}
|
||||
|
||||
function hexToString(hex){
|
||||
var arr = hex.split("")
|
||||
var out = ""
|
||||
for (var i = 0; i < arr.length / 2; i++) {
|
||||
var tmp = "0x" + arr[i * 2] + arr[i * 2 + 1]
|
||||
var charValue = String.fromCharCode(tmp);
|
||||
out += charValue
|
||||
}
|
||||
return out
|
||||
}
|
||||
|
||||
|
||||
|
||||
function admin( dev, pin ){
|
||||
if ( ! hDevice ) {
|
||||
hDevice = FISECKEY.OpenBySerial(dev, "4");
|
||||
}
|
||||
if ( ! hDevice ) {
|
||||
throw new Error("设备打开失败")
|
||||
}
|
||||
FISECKEY.ADMIN_Login(hDevice, pin);
|
||||
return hDevice;
|
||||
}
|
||||
|
||||
function login( dev, pin ){
|
||||
hDevice = FISECKEY.OpenBySerial(dev, "4");
|
||||
if ( ! hDevice ) {
|
||||
throw new Error("设备打开失败")
|
||||
}
|
||||
FISECKEY.USER_Login(hDevice, pin);
|
||||
return hDevice;
|
||||
}
|
||||
|
||||
function logout(){
|
||||
FISECKEY.USER_Logout(hDevice, 0);
|
||||
FISECKEY.CloseDevice(hDevice);
|
||||
hDevice = undefined
|
||||
}
|
||||
|
||||
function sumHash(data){
|
||||
var sum = 0;
|
||||
for (var i =0 ; i < data.length; i++) {
|
||||
sum += data.charCodeAt(i)
|
||||
}
|
||||
|
||||
sum += "";
|
||||
return sum.substr( sum.length -4 );
|
||||
}
|
||||
|
||||
function release( info ){
|
||||
if ( ! hDevice ) {
|
||||
throw new Error("设备未登录")
|
||||
}
|
||||
FISECKEY.FILE_Init(hDevice);
|
||||
|
||||
FISECKEY.FILE_CreateDir(hDevice, DIR, 0);
|
||||
|
||||
FISECKEY.FILE_CreateFile(hDevice, DIR, "name", 2048, 0);
|
||||
|
||||
var data = JSON.stringify(info)
|
||||
|
||||
writeFile(DIR, "name", data)
|
||||
|
||||
readFile(DIR, "name")
|
||||
|
||||
}
|
||||
|
||||
function readFile(dir, file) {
|
||||
if ( ! hDevice ) {
|
||||
throw new Error("设备未登录")
|
||||
}
|
||||
|
||||
var len = FISECKEY.FILE_ReadFile(hDevice, dir, file, 0, 2);
|
||||
len = parseInt( len, 10 );
|
||||
|
||||
var data = FISECKEY.FILE_ReadFile(hDevice, dir, file, 2, len);
|
||||
|
||||
var sum = sumHash(data);
|
||||
var hash = FISECKEY.FILE_ReadFile(hDevice, dir, file, 2 + len, 2);
|
||||
if ( sum === hash ) {
|
||||
|
||||
return JSON.parse(hexToString(data));
|
||||
}
|
||||
throw new Error("文件读取失败")
|
||||
}
|
||||
|
||||
function writeFile(dir, file, data){
|
||||
if ( ! hDevice ) {
|
||||
throw new Error("设备未登录")
|
||||
}
|
||||
|
||||
data = stringToHex( data ).toUpperCase()
|
||||
var len = data.length / 2
|
||||
len = "0000" + len;
|
||||
len = len.substr( len.length -4 );
|
||||
FISECKEY.FILE_WriteFile(hDevice, DIR, "name", 0, 2, len);
|
||||
FISECKEY.FILE_WriteFile(hDevice, DIR, "name", 2, data.length/2, data);
|
||||
|
||||
// console.log( "writeFile=" + len )
|
||||
// console.log( "writeFile=" + data )
|
||||
// console.log( "writeFile=" + data.length )
|
||||
|
||||
var hash = sumHash(data);
|
||||
// console.log( "writeFile hash=" + hash )
|
||||
FISECKEY.FILE_WriteFile(hDevice, DIR, "name", 2 + (data.length/2), 2, hash);
|
||||
}
|
||||
|
||||
// 枚举序列号与名称
|
||||
function enumDevByArray() {
|
||||
return FISECKEY.EnumByArray();
|
||||
}
|
||||
|
||||
|
||||
function enumDir( path ){
|
||||
if ( ! hDevice ) {
|
||||
throw new Error("设备未登录")
|
||||
}
|
||||
var folders = FISECKEY.FILE_EnmuDir(hDevice, path);
|
||||
var fos = folders.split("|")
|
||||
folders = []
|
||||
for ( var i = 0 ; i < fos.length ; i++ ) {
|
||||
if ( fos[i] ) {
|
||||
folders.push( path + "\\" + fos[i] );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
var files = FISECKEY.FILE_EnmuFile(hDevice, path);
|
||||
var fs = files.split("|")
|
||||
files = []
|
||||
for ( var i = 0 ; i < fs.length ; i++ ) {
|
||||
if ( fs[i] ) {
|
||||
files.push( path + "\\" + fs[i] );
|
||||
}
|
||||
}
|
||||
|
||||
return {
|
||||
folders : folders,
|
||||
files : files
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
function loadLMK(){
|
||||
return readFile(DIR, "lmk")
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* @param no 1/2/3
|
||||
* @param mkey HEX(48 字节)
|
||||
*/
|
||||
function saveLMK(no, lmk, pk, sk) {
|
||||
if ( ! hDevice ) {
|
||||
throw new Error("设备未登录")
|
||||
}
|
||||
|
||||
var info = {
|
||||
pk : pk , sk : sk
|
||||
}
|
||||
|
||||
switch ( no ) {
|
||||
case 1: {
|
||||
info = Object.assign( info, {
|
||||
no : no,
|
||||
lmk1 : lmk.substr(0, 32),
|
||||
lmk2 : lmk.substr(32, 64)
|
||||
})
|
||||
break;
|
||||
}
|
||||
case 2: {
|
||||
// 0 16 32 48
|
||||
// 0 32 64 96
|
||||
info = Object.assign( info, {
|
||||
no : no,
|
||||
lmk2 : lmk.substr(32, 64),
|
||||
lmk3 : lmk.substr(64, 96)
|
||||
})
|
||||
break;
|
||||
}
|
||||
case 3: {
|
||||
info = Object.assign( info, {
|
||||
no : no,
|
||||
lmk3 : lmk.substr(64, 96),
|
||||
lmk1 : lmk.substr(0, 32)
|
||||
})
|
||||
break;
|
||||
}
|
||||
default :
|
||||
throw new Error("不支持的分量")
|
||||
}
|
||||
|
||||
var data = JSON.stringify(info)
|
||||
FISECKEY.FILE_DeleteFile(hDevice, DIR, "lmk");
|
||||
FISECKEY.FILE_CreateFile(hDevice, DIR, "lmk", 2048, 0);
|
||||
writeFile( DIR, "lmk" , data);
|
||||
|
||||
|
||||
var auth = {
|
||||
uid : no,
|
||||
rid : no
|
||||
}
|
||||
|
||||
FISECKEY.FILE_DeleteFile(hDevice, DIR, "auth");
|
||||
FISECKEY.FILE_CreateFile(hDevice, DIR, "auth", 2048, 0);
|
||||
writeFile( DIR, "auth" , auth);
|
||||
}
|
||||
|
||||
function saveAuth(uid, rid){
|
||||
var auth = {
|
||||
uid : no,
|
||||
rid : no
|
||||
}
|
||||
|
||||
FISECKEY.FILE_DeleteFile(hDevice, DIR, "auth");
|
||||
FISECKEY.FILE_CreateFile(hDevice, DIR, "auth", 2048, 0);
|
||||
writeFile( DIR, "auth" , auth);
|
||||
}
|
||||
|
||||
function loadAuth(){
|
||||
return readFile(DIR, "auth")
|
||||
}
|
||||
|
||||
function catRelease(){
|
||||
return readFile(DIR, "name")
|
||||
}
|
||||
|
||||
/**
|
||||
* 修改口令
|
||||
*/
|
||||
function updatePin(oldpin, newpin){
|
||||
FISECKEY.USER_ChangePin(hDevice, 1, oldpin, newpin);
|
||||
}
|
||||
|
||||
root.UKey = {
|
||||
release: release,
|
||||
catRelease : catRelease,
|
||||
readFile: readFile,
|
||||
writeFile : writeFile,
|
||||
login : login,
|
||||
logout : logout,
|
||||
updatePin : updatePin,
|
||||
admin : admin,
|
||||
enumDevByArray : enumDevByArray,
|
||||
enumDir: enumDir,
|
||||
saveLMK : saveLMK,
|
||||
loadLMK : loadLMK,
|
||||
saveAuth : saveAuth,
|
||||
loadAuth : loadAuth
|
||||
}
|
||||
})( window )
|
||||
@@ -0,0 +1,76 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="zh-CN">
|
||||
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<meta http-equiv="X-UA-Compatible" content="IE=edge">
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0"/>
|
||||
<meta name="author" content="viggo"/>
|
||||
<title>SWA | Fullstack Club</title>
|
||||
<link rel="shortcut icon" href="../assets/images/favicon.ico">
|
||||
<link rel="stylesheet" href="http://fonts.googleapis.com/css?family=Arimo:400,700,400italic">
|
||||
<link rel="stylesheet" href="../assets/css/fonts/linecons/css/linecons.css">
|
||||
<link rel="stylesheet" href="../assets/css/fonts/fontawesome/css/font-awesome.min.css">
|
||||
<link rel="stylesheet" href="../assets/css/bootstrap.css">
|
||||
<link rel="stylesheet" href="../assets/css/xenon-core.css">
|
||||
<link rel="stylesheet" href="../assets/css/xenon-components.css">
|
||||
<link rel="stylesheet" href="../assets/css/xenon-skins.css">
|
||||
<link rel="stylesheet" href="../assets/css/nav.css">
|
||||
<link rel="stylesheet" href="../assets/css/custom-style.css">
|
||||
<script src="../assets/js/jquery-1.11.1.min.js"></script>
|
||||
<!-- HTML5 shim and Respond.js IE8 support of HTML5 elements and media queries -->
|
||||
<!--[if lt IE 9]>
|
||||
<script src="https://oss.maxcdn.com/html5shiv/3.7.2/html5shiv.min.js"></script>
|
||||
<script src="https://oss.maxcdn.com/respond/1.4.2/respond.min.js"></script>
|
||||
<![endif]-->
|
||||
</head>
|
||||
|
||||
<body class="page-body boxed-container">
|
||||
<nav class="navbar horizontal-menu navbar-fixed-top" style="height: 48px">
|
||||
<div class="navbar-inner">
|
||||
<div class="navbar-brand" style="height: 48px">
|
||||
<a href="/index.html" class="logo">
|
||||
<img src="/assets/images/bt8-expand-light.png" height="48px" alt="" class="hidden-xs">
|
||||
</a>
|
||||
</div>
|
||||
<div class="navbar-mobile-clear"></div>
|
||||
</div>
|
||||
</nav>
|
||||
<iframe id="window" src="#" width="100%" frameborder=”no” border=”0″ marginwidth=”0″ marginheight=”0″ scrolling=”no”
|
||||
allowtransparency=”yes” height="100%" style="width: 100%; height: 100%"></iframe>
|
||||
|
||||
<script type="application/javascript">
|
||||
function getQueryVariable(variable) {
|
||||
var query = window.location.search.substring(1);
|
||||
var vars = query.split("&");
|
||||
for (var i = 0; i < vars.length; i++) {
|
||||
var pair = vars[i].split("=");
|
||||
if (pair[0] == variable) {
|
||||
return pair[1];
|
||||
}
|
||||
}
|
||||
return (false);
|
||||
}
|
||||
|
||||
var url = decodeURIComponent(getQueryVariable("to"));
|
||||
document.getElementById("window").src = url;
|
||||
</script>
|
||||
|
||||
<!--<div class="page-container">-->
|
||||
<!--</div>-->
|
||||
<!-- Bottom Scripts -->
|
||||
<script src="../assets/js/bootstrap.min.js"></script>
|
||||
<script src="../assets/js/TweenMax.min.js"></script>
|
||||
<script src="../assets/js/resizeable.js"></script>
|
||||
<script src="../assets/js/joinable.js"></script>
|
||||
<script src="../assets/js/xenon-api.js"></script>
|
||||
<script src="../assets/js/xenon-toggles.js"></script>
|
||||
<!-- JavaScripts initializations and stuff -->
|
||||
<script src="../assets/js/xenon-custom.js"></script>
|
||||
<textarea tabindex="-1"
|
||||
style="position: absolute; top: -999px; left: 0px; right: auto; bottom: auto; border: 0px; padding: 0px; box-sizing: content-box; word-wrap: break-word; overflow: hidden; transition: none; height: 0px !important; min-height: 0px !important; font-family: Arimo, "Helvetica Neue", Helvetica, Arial, sans-serif; font-size: 13px; font-weight: 400; font-style: normal; letter-spacing: 0px; text-transform: none; word-spacing: 0px; text-indent: 0px; line-height: 18.5714px; width: 53px;"
|
||||
class="autosizejs" id="autosizejs"></textarea>
|
||||
</body>
|
||||
|
||||
|
||||
</html>
|
||||
Reference in New Issue
Block a user