diff --git a/Gulpfile.js b/Gulpfile.js deleted file mode 100644 index 7d5b89c..0000000 --- a/Gulpfile.js +++ /dev/null @@ -1,143 +0,0 @@ -var gulp = require('gulp'), - minifyCSS = require('gulp-minify-css'), - sass = require('gulp-sass'), - postcss = require('gulp-postcss'), - browserify = require('gulp-browserify'), - browserSync = require('browser-sync'), - uglify = require('gulp-uglify'), - rename = require('gulp-rename'), - notify = require('gulp-notify'), - replace = require('gulp-replace'), - inject = require('gulp-inject'), - svgstore = require('gulp-svgstore'), - svgmin = require('gulp-svgmin'), - plumber = require('gulp-plumber'), - eslint = require('gulp-eslint'), - jsonlint = require('gulp-jsonlint'), - beep = require('beepbeep'), - colors = require('colors'), - path = require('path'), - sourcemaps = require('gulp-sourcemaps'), - autoprefixer = require('autoprefixer'), - merge = require('merge-stream');; - -// error handling convenience wrapper -gulp.plumbedSrc = function(){ - return gulp.src.apply(gulp, arguments) - .pipe(plumber({ - errorHandler: function(err) { - beep(); - console.log('ERROR:'.bold.red); - console.log(JSON.stringify(err, null, 2).bold.red); - this.emit('end'); - } - })); -}; - -gulp.task('browser-sync', function() { - browserSync({ - server: { - baseDir: './' - }, - host: 'localhost', - port: 8000, - open: false - }); -}); - -gulp.task('sass', function () { - return gulp.plumbedSrc('./sass/**/*.scss') - .pipe(sass()) - .pipe(minifyCSS()) - .pipe(sourcemaps.init()) - .pipe(postcss([autoprefixer({ - browsers: ['last 2 versions'] - } - )])) - .pipe(sourcemaps.write('.')) - .pipe(gulp.dest('./build/css/')) - .pipe(notify({ message: 'CSS complete' })); -}); - -gulp.task('svgstore', function () { - var svgSprite = gulp.plumbedSrc('./svg/*.svg') - .pipe(svgmin(function (file) { - var prefix = path.basename(file.relative, path.extname(file.relative)); - return { - plugins: [{ - cleanupIDs: { - prefix: prefix + '-', - minify: true - } - }] - } - })) - .pipe(rename({prefix: 'svg-'})) - .pipe(svgstore({inlineSvg: true})) - .pipe(rename("social-icons.svg")) - .pipe(gulp.dest('./build/img')); - - return gulp.plumbedSrc('./index.html') - .pipe(inject(svgSprite, { - transform: function(filePath, file) { - return file.contents.toString(); - } - })) - .pipe(gulp.dest('./')); -}); - -gulp.task('scripts', function() { - var mainJS = gulp.plumbedSrc('./js/main.js') - .pipe(browserify()) - .pipe(gulp.dest('./build/js/')) - .pipe(uglify()) - .pipe(rename({ - extname: '.min.js' - })) - .pipe(replace('./build/js/*.min.js')) - .pipe(gulp.dest('./build/js')) - .pipe(notify({ message: 'JS files complete' })); - - var quoteJS = gulp.plumbedSrc('./js/quote.js') - .pipe(browserify()) - .pipe(gulp.dest('./build/js/')) - .pipe(uglify()) - .pipe(rename({ - extname: '.min.js' - })) - .pipe(replace('./build/js/*.min.js')) - .pipe(gulp.dest('./build/js')) - .pipe(notify({ message: 'JS files complete' })); - - return merge(mainJS, quoteJS); -}); - -gulp.task('scripts-watch', ['scripts'], function() { - browserSync.reload(); -}); - -gulp.task('sass-watch', ['sass'], function() { - browserSync.reload(); -}); - -gulp.task('eslint', function() { - return gulp.plumbedSrc('./js/**/*.js') - .pipe(eslint()) - .pipe(eslint.format()) - .pipe(eslint.failAfterError()) - .pipe(notify({ message: 'ESLint complete' })); -}); - -gulp.task('jsonlint', function() { - return gulp.plumbedSrc('./json/**/*.json') - .pipe(jsonlint()) - .pipe(jsonlint.failAfterError()) - .pipe(notify({ message: 'JSONLint complete' })); -}); - -gulp.task('watch', ['browser-sync'], function() { - gulp.watch('./sass/**/*.scss', ['sass-watch']); - gulp.watch('./js/*.js', ['eslint', 'scripts-watch']); -}); - -gulp.task('default', ['watch']); diff --git a/README.md b/README.md index d96abed..2f41f32 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,18 @@ -augbog.github.io -================ +# augustusyuan.com -Icons supplied from [simpleicons](https://simpleicons.org). \ No newline at end of file +Modern personal website rebuilt with React + Vite + Tailwind CSS. + +## Development + +```bash +npm install +npm run dev +``` + +## Production build + +```bash +npm run build +``` + +The custom domain is preserved by committing `CNAME` and copying it from `public/CNAME` into the built output. diff --git a/android-chrome-192x192.png b/android-chrome-192x192.png deleted file mode 100644 index 94126be..0000000 Binary files a/android-chrome-192x192.png and /dev/null differ diff --git a/android-chrome-512x512.png b/android-chrome-512x512.png deleted file mode 100644 index df22641..0000000 Binary files a/android-chrome-512x512.png and /dev/null differ diff --git a/apple-touch-icon.png b/apple-touch-icon.png deleted file mode 100644 index a31fe34..0000000 Binary files a/apple-touch-icon.png and /dev/null differ diff --git a/build/css/style.css b/build/css/style.css deleted file mode 100644 index 5d44643..0000000 --- a/build/css/style.css +++ /dev/null @@ -1,2 +0,0 @@ -.hero,header{-webkit-font-smoothing:antialiased;text-rendering:optimizeLegibility;font-family:"Helvetica Neue",helvetica,arial,sans-serif}.profile,header .profile{border-radius:50%}header{font-weight:200;position:absolute;top:0;width:100%;height:auto;z-index:3}header .header-container{display:-ms-flexbox;display:flex;margin:0 20px}header .left-align{-ms-flex-item-align:start;align-self:flex-start}header .right-align{margin-left:auto}header .secondary-nav{line-height:22px}header .mail-icon{width:15px;height:22px;vertical-align:bottom}header li{display:inline-block;height:auto;margin:0 20px}header li:first-child{margin-left:0}header li:last-child{margin-right:0}.hero{position:relative;overflow:hidden}.hero .content{position:fixed;text-align:center;width:100%;top:50%;left:50%;transform:translate(-50%,-50%);background:rgba(255,255,255,.7);padding:20px 0}.hero .evernote:focus,.hero .evernote:hover,.hero .icon:focus,.hero .icon:hover,.hero .twitch:focus,.hero .twitch:hover{transition:transform .1s ease-out 0s;transform:scale(1.2)}.hero .heading{max-width:80%;margin-left:auto;margin-right:auto;font-size:36px;font-weight:400;letter-spacing:-.5px;margin-bottom:5px}.hero .heading.quote{font-size:26px;max-width:60%}@media only screen and (max-width:600px){header{text-align:center}.hero .heading.quote{font-size:24px;max-width:80%}}.hero .job-title{font-size:20px;font-weight:200;margin-bottom:10px;vertical-align:middle}.hero .description{font-size:20px;font-weight:200;margin:0 0 20px}.hero svg{width:inherit;height:inherit}.hero .icon{display:inline-block;width:20px;height:20px;margin:0 10px}@media only screen and (max-width:600px){.hero .icon{width:30px;height:30px}}.hero .evernote,.hero .twitch{display:inline-block;width:25px;height:25px;vertical-align:bottom}.hero .evernote{fill:#666}.hero .twitch{fill:#9146ff}.hero .twitter{fill:#5EA9DD}.hero .linkedin{fill:#0077B5}.profile{width:100px}.score{font-family:monospace;font-size:30px;font-weight:800}.js-score-hidden{display:none}body,h1,h2{margin:0}ul{padding:0}li{list-style-type:none}a,a:link,a:visited{color:inherit;text-decoration:none;border-bottom:1px solid transparent}.animate-link{border-bottom:.5px solid transparent}.animate-link:hover{cursor:pointer;transition:border-color .5s ease-in 0s;border-color:rgba(0,0,0,.2)}body{transition:all .5s ease-in 0s}@media (prefers-color-scheme:dark){body{color:#fff!important;font-weight:800!important}body .github use,body .mail-icon use{fill:#fff!important}body .content{background:0 0!important}body .description,body .email,body .job-title{font-weight:400!important}} -/*# sourceMappingURL=style.css.map */ diff --git a/build/css/style.css.map b/build/css/style.css.map deleted file mode 100644 index c2a2028..0000000 --- a/build/css/style.css.map +++ /dev/null @@ -1 +0,0 @@ -{"version":3,"sources":["style.css"],"names":[],"mappings":"AAAA,aAAa,mCAAmC,kCAAkC,uDAAuD,CAAC,yBAAyB,iBAAiB,CAAC,OAAO,gBAAgB,kBAAkB,MAAM,WAAW,YAAY,SAAS,CAAC,yBAAyB,oBAAa,AAAb,aAAa,aAAa,CAAC,mBAAmB,0BAAqB,AAArB,qBAAqB,CAAC,oBAAoB,gBAAgB,CAAC,sBAAsB,gBAAgB,CAAC,kBAAkB,WAAW,YAAY,qBAAqB,CAAC,UAAU,qBAAqB,YAAY,aAAa,CAAC,sBAAsB,aAAa,CAAC,qBAAqB,cAAc,CAAC,MAAM,kBAAkB,eAAe,CAAC,eAAe,eAAe,kBAAkB,WAAW,QAAQ,SAAS,+BAA+B,gCAAgC,cAAc,CAAC,wHAAwH,qCAAqC,oBAAoB,CAAC,eAAe,cAAc,iBAAiB,kBAAkB,eAAe,gBAAgB,qBAAqB,iBAAiB,CAAC,qBAAqB,eAAe,aAAa,CAAC,yCAAyC,OAAO,iBAAiB,CAAC,qBAAqB,eAAe,aAAa,CAAC,CAAC,iBAAiB,eAAe,gBAAgB,mBAAmB,qBAAqB,CAAC,mBAAmB,eAAe,gBAAgB,eAAe,CAAC,UAAU,cAAc,cAAc,CAAC,YAAY,qBAAqB,WAAW,YAAY,aAAa,CAAC,yCAAyC,YAAY,WAAW,WAAW,CAAC,CAAC,8BAA8B,qBAAqB,WAAW,YAAY,qBAAqB,CAAC,gBAAgB,SAAS,CAAC,cAAc,YAAY,CAAC,eAAe,YAAY,CAAC,gBAAgB,YAAY,CAAC,SAAS,WAAW,CAAC,OAAO,sBAAsB,eAAe,eAAe,CAAC,iBAAiB,YAAY,CAAC,WAAW,QAAQ,CAAC,GAAG,SAAS,CAAC,GAAG,oBAAoB,CAAC,mBAAmB,cAAc,qBAAqB,mCAAmC,CAAC,cAAc,oCAAoC,CAAC,oBAAoB,eAAe,uCAAuC,2BAA2B,CAAC,KAAK,6BAA6B,CAAC,mCAAmC,KAAK,qBAAqB,yBAAyB,CAAC,qCAAqC,mBAAmB,CAAC,cAAc,wBAAwB,CAAC,8CAA8C,yBAAyB,CAAC,CAAC","file":"style.css","sourcesContent":[".hero,header{-webkit-font-smoothing:antialiased;text-rendering:optimizeLegibility;font-family:\"Helvetica Neue\",helvetica,arial,sans-serif}.profile,header .profile{border-radius:50%}header{font-weight:200;position:absolute;top:0;width:100%;height:auto;z-index:3}header .header-container{display:flex;margin:0 20px}header .left-align{align-self:flex-start}header .right-align{margin-left:auto}header .secondary-nav{line-height:22px}header .mail-icon{width:15px;height:22px;vertical-align:bottom}header li{display:inline-block;height:auto;margin:0 20px}header li:first-child{margin-left:0}header li:last-child{margin-right:0}.hero{position:relative;overflow:hidden}.hero .content{position:fixed;text-align:center;width:100%;top:50%;left:50%;transform:translate(-50%,-50%);background:rgba(255,255,255,.7);padding:20px 0}.hero .evernote:focus,.hero .evernote:hover,.hero .icon:focus,.hero .icon:hover,.hero .twitch:focus,.hero .twitch:hover{transition:transform .1s ease-out 0s;transform:scale(1.2)}.hero .heading{max-width:80%;margin-left:auto;margin-right:auto;font-size:36px;font-weight:400;letter-spacing:-.5px;margin-bottom:5px}.hero .heading.quote{font-size:26px;max-width:60%}@media only screen and (max-width:600px){header{text-align:center}.hero .heading.quote{font-size:24px;max-width:80%}}.hero .job-title{font-size:20px;font-weight:200;margin-bottom:10px;vertical-align:middle}.hero .description{font-size:20px;font-weight:200;margin:0 0 20px}.hero svg{width:inherit;height:inherit}.hero .icon{display:inline-block;width:20px;height:20px;margin:0 10px}@media only screen and (max-width:600px){.hero .icon{width:30px;height:30px}}.hero .evernote,.hero .twitch{display:inline-block;width:25px;height:25px;vertical-align:bottom}.hero .evernote{fill:#666}.hero .twitch{fill:#9146ff}.hero .twitter{fill:#5EA9DD}.hero .linkedin{fill:#0077B5}.profile{width:100px}.score{font-family:monospace;font-size:30px;font-weight:800}.js-score-hidden{display:none}body,h1,h2{margin:0}ul{padding:0}li{list-style-type:none}a,a:link,a:visited{color:inherit;text-decoration:none;border-bottom:1px solid transparent}.animate-link{border-bottom:.5px solid transparent}.animate-link:hover{cursor:pointer;transition:border-color .5s ease-in 0s;border-color:rgba(0,0,0,.2)}body{transition:all .5s ease-in 0s}@media (prefers-color-scheme:dark){body{color:#fff!important;font-weight:800!important}body .github use,body .mail-icon use{fill:#fff!important}body .content{background:0 0!important}body .description,body .email,body .job-title{font-weight:400!important}}"]} \ No newline at end of file diff --git a/build/img/social-icons.svg b/build/img/social-icons.svg deleted file mode 100644 index c3745de..0000000 --- a/build/img/social-icons.svg +++ /dev/null @@ -1 +0,0 @@ -Evernote iconTwitch icon \ No newline at end of file diff --git a/build/js/main.js b/build/js/main.js deleted file mode 100644 index 43dbe6f..0000000 --- a/build/js/main.js +++ /dev/null @@ -1,1517 +0,0 @@ -(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);throw new Error("Cannot find module '"+o+"'")}var f=n[o]={exports:{}};t[o][0].call(f.exports,function(e){var n=t[o][1][e];return s(n?n:e)},f,f.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o= 600 ? 5 : 10; - var NUM_OF_CUBES = window.innerWidth >= 600 ? 1000 : 250; - var SATISFIABLE_CUBE_SCORE = 15; - var filterCoordinates = []; - var pivot = new THREE.Group(); - var themeIndex = 0; - - var darkModeMedia = window.matchMedia('(prefers-color-scheme: dark)'); - - var cubeScore = 0; - var lineMaterial = new THREE.LineBasicMaterial({ - color: 0xffffff, - linewidth: 2 - }); - - var pivotInterval, pivotTimeout; - - var socialThemes = { - "twitter": ["#1DA1F2", "#14171A", "#657786", "#AAB8C2"], - "twitch": ["#9146ff"], - "github": ["#333", "#6e5494", "#c6e48b", "#7bc96f", "#239a3b", "#196127"], - "evernote": ['#00A82D'], - "stackoverflow": ["#f48024", "#222426", "#bcbbbb"], - "linkedin": ["#0077B5", "#00A0DC", "#313335", "#86888A"] - } - - var themes = [ - ["#042A2B", "#5EB1BF", "#CDEDF6", "#EF7B45", "#D84727"], - ["#E3E7D3", "#BDC2BF", "#989C94", "#25291C", "#E6E49F"], - ["#EAF2E3", "#61E8E1", "#F25757", "F2E863", "F2CD60"], - ['#E28413', '#F56416', '#DD4B1A', '#EF271B', '#EA1744'], - ['#86583E', '#AF2A42', '#61643F', '#AFBE96', '#F0EEE1'], - ['#D44A98', '#60B9CB', '#FFFB53'], //cmyk - ]; - - init(); - animate(); - document.getElementById("hero").appendChild(renderer.domElement); - var keepScoreElement = document.getElementsByClassName('js-increment')[0]; - - if (window.innerWidth >= 600) { - var themeHoversItemContainer = document.getElementsByClassName('content')[0]; - themeHoversItemContainer.addEventListener('mouseover', function(e) { - if (e.target && e.target.getAttribute('data-brand')) { - themifyCubes(socialThemes[e.target.getAttribute('data-brand')]); - } - }); - } - - function init() { - camera = new THREE.PerspectiveCamera( 70, window.innerWidth / window.innerHeight, 1, 10000 ); - camera.position.y = 300; - camera.position.z = window.innerWidth >= 600 ? 500 : 200; - - scene = new THREE.Scene(); - scene.add(pivot); - - raycaster = new THREE.Raycaster(); - mouse = new THREE.Vector2(); - - renderer = new THREE.WebGLRenderer(); - renderer.setClearColor(darkModeMedia.matches ? "black" : "white"); - renderer.setPixelRatio( window.devicePixelRatio ); - renderer.setSize( window.innerWidth, window.innerHeight ); - - var geometry = new THREE.BoxGeometry( CUBE_SIZE, CUBE_SIZE, CUBE_SIZE ); - geometry.colorsNeedUpdate = true; - - for (var i = 0; i < NUM_OF_CUBES; i++) { - var randomColor = Math.random() * 0xffffff; - // generate random coordinates that are not already occupied yet - var coordinates = generateRandomCoords(filterCoordinates); - objects[i] = new THREE.Mesh( geometry, new THREE.MeshBasicMaterial( { color: new THREE.Color(randomColor), opacity: 0.6, transparent: true, depthWrite: false } ) ); - objects[i].position.set(coordinates.x, coordinates.y, coordinates.z); - - // add to filter so we do not generate conflicting coordinates again - filterCoordinates.push(coordinates); - - // modify rotation - objects[i].rotation.x = Math.random() * 2 * Math.PI; - objects[i].rotation.y = Math.random() * 2 * Math.PI; - pivot.add( objects[i] ); - - var edges = new THREE.EdgesGeometry( geometry ); - var line = new THREE.LineSegments(edges, lineMaterial); - objects[i].add(line); - } - - document.addEventListener( 'keyup', onKeyUp, false ); - document.addEventListener('mousemove', onDocumentMouseMove, false); - - if (window.DeviceOrientationEvent) { - window.addEventListener( 'deviceorientation', onDeviceOrientation, false ); - } - window.addEventListener( 'resize', onWindowResize, false ); - - // Detect dark mode only supported in Safari 12.1 - if (darkModeMedia.matches) { - setColorScheme({ darkMode: true, shouldTransition: false }); - } - darkModeMedia.addListener(function(e) { - var colorSchemeOptions = { - darkMode: darkModeMedia.matches, - shouldTransition: true, - } - setColorScheme(colorSchemeOptions); - //darkModeMedia.matches ? darkMode() : lightMode(); - }); - - if (window.innerWidth > 600 || !window.DeviceOrientationEvent) { - if (pivotInterval) { - clearInterval(pivotInterval); - } - if (pivotTimeout) { - clearTimeout(pivotTimeout); - } - // set time shift - pivotInterval = setInterval(function() { - PIVOT_SPEED = 0.2; - var pivotTimeout = setTimeout(function() { - PIVOT_SPEED = 0.02; - }, 750) - }, 12000); - } - } - - function onWindowResize() { - if (pivotInterval) { - clearInterval(pivotInterval); - } - if (pivotTimeout) { - clearTimeout(pivotTimeout); - } - - camera.aspect = window.innerWidth / window.innerHeight; - camera.updateProjectionMatrix(); - - renderer.setSize( window.innerWidth, window.innerHeight ); - renderer.render( scene, camera ); - } - - function onKeyUp(e) { - themeIndex = (themeIndex + 1) % themes.length; - if (e.key.includes('Arrow')) { - themifyCubes(themes[themeIndex]); - } - } - - function onDeviceOrientation( event ) { - // set camera to change its view based on gyroscope - // NOTE: adding 100 to beta starts the phone as if it were vertical - var vectorAngle = new THREE.Vector3( - RADIUS * Math.sin(THREE.Math.degToRad( event.alpha ))*-1, - RADIUS * Math.sin(THREE.Math.degToRad( event.beta + 100 ))*-1, - scene.position.z - ) - camera.lookAt(vectorAngle); - - raycaster.setFromCamera( mouse, camera ); - renderer.render( scene, camera ); - } - - function onDocumentMouseMove(event) { - event.preventDefault(); - mouse.x = event.clientX / window.innerWidth * 2 - 1; - mouse.y = -(event.clientY / window.innerHeight) * 2 + 1; - - // if user hovers over specific cube, TWEEN scale to make it pop - raycaster.setFromCamera(mouse, camera); - var intersects = raycaster.intersectObjects(objects); - - // check we have intersects and that the uuid of the object is not already tweening - if (intersects.length > 0) { - if (!INTERSECTED[intersects[0].object.uuid]) { - INTERSECTED[intersects[0].object.uuid] = intersects[0].object; - var scaleTween = new TWEEN.Tween(intersects[0].object.scale) - .to({ x: 3, y: 3, z: 3 }, 500) - .easing(TWEEN.Easing.Elastic.Out); - var rotationTween = new TWEEN.Tween(intersects[0].object.rotation) - .to({ x: Math.random(), y: Math.random(), z: Math.random() }, 500) - .easing(TWEEN.Easing.Elastic.Out) - var shrinkTween = new TWEEN.Tween(intersects[0].object.scale) - .to({ x: 1, y: 1, z: 1 }, 500) - .delay(1000) - .easing(TWEEN.Easing.Elastic.Out) - .onComplete(function(tween) { - var uuid = Object.keys(INTERSECTED).shift(); - delete INTERSECTED[uuid]; - }); - scaleTween.chain(shrinkTween).start(); - rotationTween.start(); - incrementScore(); - } - } - } - - function animate() { - requestAnimationFrame( animate ); - TWEEN.update(); - render(); - } - - function render() { - // in order to prevent the theta from forever growing which could hit Number.MAX_SAFE_INTEGER, - // go reverse and interchange - if (multiplier > 0 && theta >= 100) { - multiplier = -1; - } else if (multiplier < 0 && theta <= 0) { - multiplier = 1; - } - theta += PIVOT_SPEED * multiplier; - - pivot.rotation.set( - Math.sin( THREE.Math.degToRad( theta )), - Math.sin( THREE.Math.degToRad( theta )), - Math.sin( THREE.Math.degToRad( theta )) - ); - - raycaster.setFromCamera( mouse, camera ); - renderer.render( scene, camera ); - } - - // generate random coordinates based on page and size of cubes - // TODO: handle filtering of coordinates - function generateRandomCoords(filterCoordinates) { - var coords = { - x: (Math.random() * 800 - 200), - y: (Math.random() * 800 - 200), - z: (Math.random() * 800 - 200) - }; - - return coords; - } - - // takes in an array of hex colors and applies the theme equally to the cubes - function themifyCubes(theme) { - if (!theme) { - for (var i = 0; i < objects.length; i++) { - var randomColor = Math.random() * 0xffffff; - objects[i].material.color.set(new THREE.Color(randomColor)); - } - } else { - for (var i = 0; i < objects.length; i++) { - var hexColor = parseInt(theme[i % theme.length].replace("#", "0x"), 16); - objects[i].material.color.set(new THREE.Color(hexColor)); - } - } - } - - /** - * Sets the color scheme - * options: { darkMode: boolean, shouldTransition: boolean } - */ - function setColorScheme(options) { - var whiteClearColor = new THREE.Color("white"); - var darkClearColor = new THREE.Color("black"); - var firstClearColor = options.darkMode ? whiteClearColor : darkClearColor; - var transitionedClearColor = options.darkMode ? darkClearColor : whiteClearColor; - if (options.shouldTransition) { - var colorModeTween = new TWEEN.Tween(firstClearColor) - .to(transitionedClearColor, 500).onUpdate(function() { - renderer.setClearColor(firstClearColor); - }).start(); - } else { - renderer.setClearColor(transitionedClearColor); - } - if (options.darkMode) { - document.body.classList.add("dark-mode"); - } else { - document.body.classList.remove("dark-mode"); - } - lineMaterial = new THREE.LineBasicMaterial({ - color: options.darkMode ? 0x000000 : 0xffffff, - linewidth: 2 - }); - var geometry = new THREE.BoxGeometry( CUBE_SIZE, CUBE_SIZE, CUBE_SIZE ); - geometry.colorsNeedUpdate = true; - var edges = new THREE.EdgesGeometry( geometry ); - for (var i = 0; i < objects.length; i++) { - var line = new THREE.LineSegments(edges, lineMaterial); - objects[i].add(line); - } - render(); - } - - // flicker cubes through all the themes twice! :) - function flickerCubes() { - var ran = false; - var i = 0; - var index = 0; - while (i++ < themes.length) { - var theme = themes[i]; - if (i === themes.length - 1 && !ran) { - ran = true; - i = 0; - } else if (i === themes.length - 1) { - theme = false; - } - (function(i) { - setTimeout(function() { - themifyCubes(theme); - }, index++ * 200); - })(i); - } - } - - // Handy function to handle logarithmic function - function getBaseLog(x, y) { - return Math.log(y) / Math.log(x); - } - - // Blow up all the cubes in logarithmic fashion so as time goes on, we blow up more - function blowUpCubes() { - var shrinkTweens = []; - for (var i = 0; i < objects.length; i+=2) { - var delay = Math.floor(getBaseLog(2, i) * 200); - var scaleTween = new TWEEN.Tween(objects[i].scale) - .delay(delay) - .to({ x: 3, y: 3, z: 3 }, 500) - .easing(TWEEN.Easing.Elastic.Out).onComplete(function() { - shrinkTween.start(); - }); - var rotationTween = new TWEEN.Tween(objects[i].rotation) - .delay(delay) - .to({ x: Math.random(), y: Math.random(), z: Math.random() }, 500) - .easing(TWEEN.Easing.Elastic.Out) - var shrinkTween = new TWEEN.Tween(objects[i].scale) - .delay(Math.floor(getBaseLog(2, Math.floor(objects.length / 2)) * 200)) - .to({ x: 1, y: 1, z: 1 }, 500) - .easing(TWEEN.Easing.Elastic.Out); - scaleTween.chain(shrinkTween).start(); - rotationTween.start(); - } - } - - function incrementScore() { - cubeScore++; - keepScoreElement.innerText = cubeScore; - if (cubeScore >= SATISFIABLE_CUBE_SCORE && document.getElementsByClassName('js-score-hidden').length > 0) { - document.getElementsByClassName('js-score-hidden')[0].classList.remove('js-score-hidden'); - } else if (cubeScore % 100 === 0) { - flickerCubes(); - } - } -})(); - -},{"./quote.js":2,"@tweenjs/tween.js":4,"konami-komando":5}],2:[function(require,module,exports){ -(function() { - var quotes = require('../json/quotes.json'); - var quoteTrigger = document.getElementById('quotes'); - - String.prototype.typeout = function(targetElem) { - var timer; - var str = this.split(''); - var strCopy = str.slice(0); - clearTimeout(timer); - var ll = ''; - (function shuffle(start){ - // This code is run options.fps times per second - // and updates the contents of the page element - var i, len = strCopy.length; - if(start>=len){ - return targetElem.innerHTML = str.join('').toString();// you can use your selectors - } - ll = ll + strCopy[start]; - targetElem.innerHTML = ll; // you can use your selectors - timer = setTimeout(function(){ - shuffle(start+1); - }, 50); - })(0); - } - - function triggerQuoteAnimation() { - var heading = document.getElementsByClassName('heading')[0]; - var description = document.getElementsByClassName('description')[0]; - var jobTitle = document.getElementsByClassName("job-title")[0]; - heading.className = 'heading quote'; - description.className = 'description author'; - jobTitle.style.display = 'none'; - - var oHeading = heading.innerText; - var oDescription = description.innerText; - for (var i=0; i<=quotes.length; i++) { - (function(i) { - if (i == quotes.length) { - setTimeout(function(e) { - heading.className = 'heading'; - description.className = 'description'; - description.innerHTML = ''; - oHeading.typeout(heading); - }, 10000*i); - setTimeout(function(e) { - oDescription.typeout(description); - jobTitle.style = ''; - }, 10000*i+2000); - quoteTrigger.removeEventListener('click', triggerQuoteAnimation); - } else { - var quote = new String(quotes[i].quote); - var author = new String(quotes[i].author); - setTimeout(function(e) { - var moddedQuote = '“' + quote + '”'; - moddedQuote.typeout(heading); - description.innerHTML = ''; - }, 10000*i); - setTimeout(function(e) { - author.typeout(description); - }, 10000*i+2000); - } - })(i); - } - } - - quoteTrigger.addEventListener('click', triggerQuoteAnimation); -})(); -},{"../json/quotes.json":3}],3:[function(require,module,exports){ -module.exports=[ - { - "quote" : "Fairy tales are more than true — not because they tell us dragons exist, but because they tell us dragons can be beaten.", - "author": "G. K. Chesterton" - }, - { - "quote" : "Don't go through life, grow through life.", - "author": "Eric Butterworth" - }, - { - "quote" : "Wisdom is knowing what to do next, skill is knowing how to do it, and virtue is doing it.", - "author": "David Starr Jordan" - }, - { - "quote": "Never doubt that a small group of thoughtful, committed, citizens can change the world. Indeed, it is the only thing that ever has.", - "author": "Margaret Mead" - }, - { - "quote": "When we speak we are afraid our words will not be heard or welcomed. But when we are silent, we are still afraid. So it is better to speak.", - "author": "Audre Lorde" - } -] - - -},{}],4:[function(require,module,exports){ -(function (process){ -/** - * Tween.js - Licensed under the MIT license - * https://github.com/tweenjs/tween.js - * ---------------------------------------------- - * - * See https://github.com/tweenjs/tween.js/graphs/contributors for the full list of contributors. - * Thank you all, you're awesome! - */ - - -var _Group = function () { - this._tweens = {}; - this._tweensAddedDuringUpdate = {}; -}; - -_Group.prototype = { - getAll: function () { - - return Object.keys(this._tweens).map(function (tweenId) { - return this._tweens[tweenId]; - }.bind(this)); - - }, - - removeAll: function () { - - this._tweens = {}; - - }, - - add: function (tween) { - - this._tweens[tween.getId()] = tween; - this._tweensAddedDuringUpdate[tween.getId()] = tween; - - }, - - remove: function (tween) { - - delete this._tweens[tween.getId()]; - delete this._tweensAddedDuringUpdate[tween.getId()]; - - }, - - update: function (time, preserve) { - - var tweenIds = Object.keys(this._tweens); - - if (tweenIds.length === 0) { - return false; - } - - time = time !== undefined ? time : TWEEN.now(); - - // Tweens are updated in "batches". If you add a new tween during an update, then the - // new tween will be updated in the next batch. - // If you remove a tween during an update, it may or may not be updated. However, - // if the removed tween was added during the current batch, then it will not be updated. - while (tweenIds.length > 0) { - this._tweensAddedDuringUpdate = {}; - - for (var i = 0; i < tweenIds.length; i++) { - - var tween = this._tweens[tweenIds[i]]; - - if (tween && tween.update(time) === false) { - tween._isPlaying = false; - - if (!preserve) { - delete this._tweens[tweenIds[i]]; - } - } - } - - tweenIds = Object.keys(this._tweensAddedDuringUpdate); - } - - return true; - - } -}; - -var TWEEN = new _Group(); - -TWEEN.Group = _Group; -TWEEN._nextId = 0; -TWEEN.nextId = function () { - return TWEEN._nextId++; -}; - - -// Include a performance.now polyfill. -// In node.js, use process.hrtime. -if (typeof (self) === 'undefined' && typeof (process) !== 'undefined' && process.hrtime) { - TWEEN.now = function () { - var time = process.hrtime(); - - // Convert [seconds, nanoseconds] to milliseconds. - return time[0] * 1000 + time[1] / 1000000; - }; -} -// In a browser, use self.performance.now if it is available. -else if (typeof (self) !== 'undefined' && - self.performance !== undefined && - self.performance.now !== undefined) { - // This must be bound, because directly assigning this function - // leads to an invocation exception in Chrome. - TWEEN.now = self.performance.now.bind(self.performance); -} -// Use Date.now if it is available. -else if (Date.now !== undefined) { - TWEEN.now = Date.now; -} -// Otherwise, use 'new Date().getTime()'. -else { - TWEEN.now = function () { - return new Date().getTime(); - }; -} - - -TWEEN.Tween = function (object, group) { - this._object = object; - this._valuesStart = {}; - this._valuesEnd = {}; - this._valuesStartRepeat = {}; - this._duration = 1000; - this._repeat = 0; - this._repeatDelayTime = undefined; - this._yoyo = false; - this._isPlaying = false; - this._reversed = false; - this._delayTime = 0; - this._startTime = null; - this._easingFunction = TWEEN.Easing.Linear.None; - this._interpolationFunction = TWEEN.Interpolation.Linear; - this._chainedTweens = []; - this._onStartCallback = null; - this._onStartCallbackFired = false; - this._onUpdateCallback = null; - this._onRepeatCallback = null; - this._onCompleteCallback = null; - this._onStopCallback = null; - this._group = group || TWEEN; - this._id = TWEEN.nextId(); - -}; - -TWEEN.Tween.prototype = { - getId: function () { - return this._id; - }, - - isPlaying: function () { - return this._isPlaying; - }, - - to: function (properties, duration) { - - this._valuesEnd = Object.create(properties); - - if (duration !== undefined) { - this._duration = duration; - } - - return this; - - }, - - duration: function duration(d) { - this._duration = d; - return this; - }, - - start: function (time) { - - this._group.add(this); - - this._isPlaying = true; - - this._onStartCallbackFired = false; - - this._startTime = time !== undefined ? typeof time === 'string' ? TWEEN.now() + parseFloat(time) : time : TWEEN.now(); - this._startTime += this._delayTime; - - for (var property in this._valuesEnd) { - - // Check if an Array was provided as property value - if (this._valuesEnd[property] instanceof Array) { - - if (this._valuesEnd[property].length === 0) { - continue; - } - - // Create a local copy of the Array with the start value at the front - this._valuesEnd[property] = [this._object[property]].concat(this._valuesEnd[property]); - - } - - // If `to()` specifies a property that doesn't exist in the source object, - // we should not set that property in the object - if (this._object[property] === undefined) { - continue; - } - - // Save the starting value. - this._valuesStart[property] = this._object[property]; - - if ((this._valuesStart[property] instanceof Array) === false) { - this._valuesStart[property] *= 1.0; // Ensures we're using numbers, not strings - } - - this._valuesStartRepeat[property] = this._valuesStart[property] || 0; - - } - - return this; - - }, - - stop: function () { - - if (!this._isPlaying) { - return this; - } - - this._group.remove(this); - this._isPlaying = false; - - if (this._onStopCallback !== null) { - this._onStopCallback(this._object); - } - - this.stopChainedTweens(); - return this; - - }, - - end: function () { - - this.update(Infinity); - return this; - - }, - - stopChainedTweens: function () { - - for (var i = 0, numChainedTweens = this._chainedTweens.length; i < numChainedTweens; i++) { - this._chainedTweens[i].stop(); - } - - }, - - group: function (group) { - this._group = group; - return this; - }, - - delay: function (amount) { - - this._delayTime = amount; - return this; - - }, - - repeat: function (times) { - - this._repeat = times; - return this; - - }, - - repeatDelay: function (amount) { - - this._repeatDelayTime = amount; - return this; - - }, - - yoyo: function (yoyo) { - - this._yoyo = yoyo; - return this; - - }, - - easing: function (easingFunction) { - - this._easingFunction = easingFunction; - return this; - - }, - - interpolation: function (interpolationFunction) { - - this._interpolationFunction = interpolationFunction; - return this; - - }, - - chain: function () { - - this._chainedTweens = arguments; - return this; - - }, - - onStart: function (callback) { - - this._onStartCallback = callback; - return this; - - }, - - onUpdate: function (callback) { - - this._onUpdateCallback = callback; - return this; - - }, - - onRepeat: function onRepeat(callback) { - - this._onRepeatCallback = callback; - return this; - - }, - - onComplete: function (callback) { - - this._onCompleteCallback = callback; - return this; - - }, - - onStop: function (callback) { - - this._onStopCallback = callback; - return this; - - }, - - update: function (time) { - - var property; - var elapsed; - var value; - - if (time < this._startTime) { - return true; - } - - if (this._onStartCallbackFired === false) { - - if (this._onStartCallback !== null) { - this._onStartCallback(this._object); - } - - this._onStartCallbackFired = true; - } - - elapsed = (time - this._startTime) / this._duration; - elapsed = (this._duration === 0 || elapsed > 1) ? 1 : elapsed; - - value = this._easingFunction(elapsed); - - for (property in this._valuesEnd) { - - // Don't update properties that do not exist in the source object - if (this._valuesStart[property] === undefined) { - continue; - } - - var start = this._valuesStart[property] || 0; - var end = this._valuesEnd[property]; - - if (end instanceof Array) { - - this._object[property] = this._interpolationFunction(end, value); - - } else { - - // Parses relative end values with start as base (e.g.: +10, -3) - if (typeof (end) === 'string') { - - if (end.charAt(0) === '+' || end.charAt(0) === '-') { - end = start + parseFloat(end); - } else { - end = parseFloat(end); - } - } - - // Protect against non numeric properties. - if (typeof (end) === 'number') { - this._object[property] = start + (end - start) * value; - } - - } - - } - - if (this._onUpdateCallback !== null) { - this._onUpdateCallback(this._object, elapsed); - } - - if (elapsed === 1) { - - if (this._repeat > 0) { - - if (isFinite(this._repeat)) { - this._repeat--; - } - - // Reassign starting values, restart by making startTime = now - for (property in this._valuesStartRepeat) { - - if (typeof (this._valuesEnd[property]) === 'string') { - this._valuesStartRepeat[property] = this._valuesStartRepeat[property] + parseFloat(this._valuesEnd[property]); - } - - if (this._yoyo) { - var tmp = this._valuesStartRepeat[property]; - - this._valuesStartRepeat[property] = this._valuesEnd[property]; - this._valuesEnd[property] = tmp; - } - - this._valuesStart[property] = this._valuesStartRepeat[property]; - - } - - if (this._yoyo) { - this._reversed = !this._reversed; - } - - if (this._repeatDelayTime !== undefined) { - this._startTime = time + this._repeatDelayTime; - } else { - this._startTime = time + this._delayTime; - } - - if (this._onRepeatCallback !== null) { - this._onRepeatCallback(this._object); - } - - return true; - - } else { - - if (this._onCompleteCallback !== null) { - - this._onCompleteCallback(this._object); - } - - for (var i = 0, numChainedTweens = this._chainedTweens.length; i < numChainedTweens; i++) { - // Make the chained tweens start exactly at the time they should, - // even if the `update()` method was called way past the duration of the tween - this._chainedTweens[i].start(this._startTime + this._duration); - } - - return false; - - } - - } - - return true; - - } -}; - - -TWEEN.Easing = { - - Linear: { - - None: function (k) { - - return k; - - } - - }, - - Quadratic: { - - In: function (k) { - - return k * k; - - }, - - Out: function (k) { - - return k * (2 - k); - - }, - - InOut: function (k) { - - if ((k *= 2) < 1) { - return 0.5 * k * k; - } - - return - 0.5 * (--k * (k - 2) - 1); - - } - - }, - - Cubic: { - - In: function (k) { - - return k * k * k; - - }, - - Out: function (k) { - - return --k * k * k + 1; - - }, - - InOut: function (k) { - - if ((k *= 2) < 1) { - return 0.5 * k * k * k; - } - - return 0.5 * ((k -= 2) * k * k + 2); - - } - - }, - - Quartic: { - - In: function (k) { - - return k * k * k * k; - - }, - - Out: function (k) { - - return 1 - (--k * k * k * k); - - }, - - InOut: function (k) { - - if ((k *= 2) < 1) { - return 0.5 * k * k * k * k; - } - - return - 0.5 * ((k -= 2) * k * k * k - 2); - - } - - }, - - Quintic: { - - In: function (k) { - - return k * k * k * k * k; - - }, - - Out: function (k) { - - return --k * k * k * k * k + 1; - - }, - - InOut: function (k) { - - if ((k *= 2) < 1) { - return 0.5 * k * k * k * k * k; - } - - return 0.5 * ((k -= 2) * k * k * k * k + 2); - - } - - }, - - Sinusoidal: { - - In: function (k) { - - return 1 - Math.cos(k * Math.PI / 2); - - }, - - Out: function (k) { - - return Math.sin(k * Math.PI / 2); - - }, - - InOut: function (k) { - - return 0.5 * (1 - Math.cos(Math.PI * k)); - - } - - }, - - Exponential: { - - In: function (k) { - - return k === 0 ? 0 : Math.pow(1024, k - 1); - - }, - - Out: function (k) { - - return k === 1 ? 1 : 1 - Math.pow(2, - 10 * k); - - }, - - InOut: function (k) { - - if (k === 0) { - return 0; - } - - if (k === 1) { - return 1; - } - - if ((k *= 2) < 1) { - return 0.5 * Math.pow(1024, k - 1); - } - - return 0.5 * (- Math.pow(2, - 10 * (k - 1)) + 2); - - } - - }, - - Circular: { - - In: function (k) { - - return 1 - Math.sqrt(1 - k * k); - - }, - - Out: function (k) { - - return Math.sqrt(1 - (--k * k)); - - }, - - InOut: function (k) { - - if ((k *= 2) < 1) { - return - 0.5 * (Math.sqrt(1 - k * k) - 1); - } - - return 0.5 * (Math.sqrt(1 - (k -= 2) * k) + 1); - - } - - }, - - Elastic: { - - In: function (k) { - - if (k === 0) { - return 0; - } - - if (k === 1) { - return 1; - } - - return -Math.pow(2, 10 * (k - 1)) * Math.sin((k - 1.1) * 5 * Math.PI); - - }, - - Out: function (k) { - - if (k === 0) { - return 0; - } - - if (k === 1) { - return 1; - } - - return Math.pow(2, -10 * k) * Math.sin((k - 0.1) * 5 * Math.PI) + 1; - - }, - - InOut: function (k) { - - if (k === 0) { - return 0; - } - - if (k === 1) { - return 1; - } - - k *= 2; - - if (k < 1) { - return -0.5 * Math.pow(2, 10 * (k - 1)) * Math.sin((k - 1.1) * 5 * Math.PI); - } - - return 0.5 * Math.pow(2, -10 * (k - 1)) * Math.sin((k - 1.1) * 5 * Math.PI) + 1; - - } - - }, - - Back: { - - In: function (k) { - - var s = 1.70158; - - return k * k * ((s + 1) * k - s); - - }, - - Out: function (k) { - - var s = 1.70158; - - return --k * k * ((s + 1) * k + s) + 1; - - }, - - InOut: function (k) { - - var s = 1.70158 * 1.525; - - if ((k *= 2) < 1) { - return 0.5 * (k * k * ((s + 1) * k - s)); - } - - return 0.5 * ((k -= 2) * k * ((s + 1) * k + s) + 2); - - } - - }, - - Bounce: { - - In: function (k) { - - return 1 - TWEEN.Easing.Bounce.Out(1 - k); - - }, - - Out: function (k) { - - if (k < (1 / 2.75)) { - return 7.5625 * k * k; - } else if (k < (2 / 2.75)) { - return 7.5625 * (k -= (1.5 / 2.75)) * k + 0.75; - } else if (k < (2.5 / 2.75)) { - return 7.5625 * (k -= (2.25 / 2.75)) * k + 0.9375; - } else { - return 7.5625 * (k -= (2.625 / 2.75)) * k + 0.984375; - } - - }, - - InOut: function (k) { - - if (k < 0.5) { - return TWEEN.Easing.Bounce.In(k * 2) * 0.5; - } - - return TWEEN.Easing.Bounce.Out(k * 2 - 1) * 0.5 + 0.5; - - } - - } - -}; - -TWEEN.Interpolation = { - - Linear: function (v, k) { - - var m = v.length - 1; - var f = m * k; - var i = Math.floor(f); - var fn = TWEEN.Interpolation.Utils.Linear; - - if (k < 0) { - return fn(v[0], v[1], f); - } - - if (k > 1) { - return fn(v[m], v[m - 1], m - f); - } - - return fn(v[i], v[i + 1 > m ? m : i + 1], f - i); - - }, - - Bezier: function (v, k) { - - var b = 0; - var n = v.length - 1; - var pw = Math.pow; - var bn = TWEEN.Interpolation.Utils.Bernstein; - - for (var i = 0; i <= n; i++) { - b += pw(1 - k, n - i) * pw(k, i) * v[i] * bn(n, i); - } - - return b; - - }, - - CatmullRom: function (v, k) { - - var m = v.length - 1; - var f = m * k; - var i = Math.floor(f); - var fn = TWEEN.Interpolation.Utils.CatmullRom; - - if (v[0] === v[m]) { - - if (k < 0) { - i = Math.floor(f = m * (1 + k)); - } - - return fn(v[(i - 1 + m) % m], v[i], v[(i + 1) % m], v[(i + 2) % m], f - i); - - } else { - - if (k < 0) { - return v[0] - (fn(v[0], v[0], v[1], v[1], -f) - v[0]); - } - - if (k > 1) { - return v[m] - (fn(v[m], v[m], v[m - 1], v[m - 1], f - m) - v[m]); - } - - return fn(v[i ? i - 1 : 0], v[i], v[m < i + 1 ? m : i + 1], v[m < i + 2 ? m : i + 2], f - i); - - } - - }, - - Utils: { - - Linear: function (p0, p1, t) { - - return (p1 - p0) * t + p0; - - }, - - Bernstein: function (n, i) { - - var fc = TWEEN.Interpolation.Utils.Factorial; - - return fc(n) / fc(i) / fc(n - i); - - }, - - Factorial: (function () { - - var a = [1]; - - return function (n) { - - var s = 1; - - if (a[n]) { - return a[n]; - } - - for (var i = n; i > 1; i--) { - s *= i; - } - - a[n] = s; - return s; - - }; - - })(), - - CatmullRom: function (p0, p1, p2, p3, t) { - - var v0 = (p2 - p0) * 0.5; - var v1 = (p3 - p1) * 0.5; - var t2 = t * t; - var t3 = t * t2; - - return (2 * p1 - 2 * p2 + v0 + v1) * t3 + (- 3 * p1 + 3 * p2 - 2 * v0 - v1) * t2 + v0 * t + p1; - - } - - } - -}; - -// UMD (Universal Module Definition) -(function (root) { - - if (typeof define === 'function' && define.amd) { - - // AMD - define([], function () { - return TWEEN; - }); - - } else if (typeof module !== 'undefined' && typeof exports === 'object') { - - // Node.js - module.exports = TWEEN; - - } else if (root !== undefined) { - - // Global variable - root.TWEEN = TWEEN; - - } - -})(this); - -}).call(this,require("pBGvAp")) -},{"pBGvAp":6}],5:[function(require,module,exports){ -var konami = function(opts) { - if (typeof opts.once === "undefined") { - opts.once = true; - } - - if (typeof opts.useCapture === "undefined") { - opts.useCapture = true; - } - - if (typeof opts.callback !== "function") { - throw new Error("Konami: callback is not a function."); - return; - } - - var ran = false; - var keypresses = []; - var KONAMI_CODE = [38, 38, 40, 40, 37, 39, 37, 39, 66, 65]; - - document.addEventListener('keydown', function(e) { - if (opts.once && ran) { - return; - } - - var key = (function(e) { - var event = e || window.event; - return (event.keyCode || event.which); - })(e); - - // if first button isn't up, return - if (keypresses.length == 0 && key != 38) { - return; - // if valid konami code character and keypresses available - } else if (keypresses.length < 10 && /37|38|39|40|65|66/.test(key)) { - keypresses.push(key); - if (keypresses.length == 10 - && JSON.stringify(keypresses) == JSON.stringify(KONAMI_CODE)) { - opts.callback(); - if (opts.once) { - ran = true; - } - } - } else { - keypresses = []; - } - }, opts.useCapture); -}; - -module.exports = konami; - -},{}],6:[function(require,module,exports){ -// shim for using process in browser - -var process = module.exports = {}; - -process.nextTick = (function () { - var canSetImmediate = typeof window !== 'undefined' - && window.setImmediate; - var canPost = typeof window !== 'undefined' - && window.postMessage && window.addEventListener - ; - - if (canSetImmediate) { - return function (f) { return window.setImmediate(f) }; - } - - if (canPost) { - var queue = []; - window.addEventListener('message', function (ev) { - var source = ev.source; - if ((source === window || source === null) && ev.data === 'process-tick') { - ev.stopPropagation(); - if (queue.length > 0) { - var fn = queue.shift(); - fn(); - } - } - }, true); - - return function nextTick(fn) { - queue.push(fn); - window.postMessage('process-tick', '*'); - }; - } - - return function nextTick(fn) { - setTimeout(fn, 0); - }; -})(); - -process.title = 'browser'; -process.browser = true; -process.env = {}; -process.argv = []; - -function noop() {} - -process.on = noop; -process.addListener = noop; -process.once = noop; -process.off = noop; -process.removeListener = noop; -process.removeAllListeners = noop; -process.emit = noop; - -process.binding = function (name) { - throw new Error('process.binding is not supported'); -} - -// TODO(shtylman) -process.cwd = function () { return '/' }; -process.chdir = function (dir) { - throw new Error('process.chdir is not supported'); -}; - -},{}]},{},[1]) \ No newline at end of file diff --git a/build/js/main.min.js b/build/js/main.min.js deleted file mode 100644 index 1708427..0000000 --- a/build/js/main.min.js +++ /dev/null @@ -1 +0,0 @@ -!function t(e,n,i){function o(a,s){if(!n[a]){if(!e[a]){var u="function"==typeof require&&require;if(!s&&u)return u(a,!0);if(r)return r(a,!0);throw new Error("Cannot find module '"+a+"'")}var c=n[a]={exports:{}};e[a][0].call(c.exports,function(t){var n=e[a][1][t];return o(n?n:t)},c,c.exports,t,e,n,i)}return n[a].exports}for(var r="function"==typeof require&&require,a=0;a=600?500:200,v=new THREE.Scene,v.add(O),g=new THREE.Raycaster,T=new THREE.Vector2,E=new THREE.WebGLRenderer,E.setClearColor(A.matches?"black":"white"),E.setPixelRatio(window.devicePixelRatio),E.setSize(window.innerWidth,window.innerHeight);var t=new THREE.BoxGeometry(S,S,S);t.colorsNeedUpdate=!0;for(var e=0;e600||!window.DeviceOrientationEvent)&&(_&&clearInterval(_),y&&clearTimeout(y),_=setInterval(function(){k=.2;setTimeout(function(){k=.02},750)},12e3))}function n(){_&&clearInterval(_),y&&clearTimeout(y),m.aspect=window.innerWidth/window.innerHeight,m.updateProjectionMatrix(),E.setSize(window.innerWidth,window.innerHeight),E.render(v,m)}function i(t){H=(H+1)%q.length,t.key.includes("Arrow")&&c(q[H])}function o(t){var e=new THREE.Vector3(I*Math.sin(THREE.Math.degToRad(t.alpha))*-1,I*Math.sin(THREE.Math.degToRad(t.beta+100))*-1,v.position.z);m.lookAt(e),g.setFromCamera(T,m),E.render(v,m)}function r(t){t.preventDefault(),T.x=t.clientX/window.innerWidth*2-1,T.y=2*-(t.clientY/window.innerHeight)+1,g.setFromCamera(T,m);var e=g.intersectObjects(C);if(e.length>0&&!b[e[0].object.uuid]){b[e[0].object.uuid]=e[0].object;var n=new p.Tween(e[0].object.scale).to({x:3,y:3,z:3},500).easing(p.Easing.Elastic.Out),i=new p.Tween(e[0].object.rotation).to({x:Math.random(),y:Math.random(),z:Math.random()},500).easing(p.Easing.Elastic.Out),o=new p.Tween(e[0].object.scale).to({x:1,y:1,z:1},500).delay(1e3).easing(p.Easing.Elastic.Out).onComplete(function(t){var e=Object.keys(b).shift();delete b[e]});n.chain(o).start(),i.start(),w()}}function a(){requestAnimationFrame(a),p.update(),s()}function s(){M>0&&R>=100?M=-1:M<0&&R<=0&&(M=1),R+=k*M,O.rotation.set(Math.sin(THREE.Math.degToRad(R)),Math.sin(THREE.Math.degToRad(R)),Math.sin(THREE.Math.degToRad(R))),g.setFromCamera(T,m),E.render(v,m)}function u(t){var e={x:800*Math.random()-200,y:800*Math.random()-200,z:800*Math.random()-200};return e}function c(t){if(t)for(var e=0;e=F&&document.getElementsByClassName("js-score-hidden").length>0?document.getElementsByClassName("js-score-hidden")[0].classList.remove("js-score-hidden"):x%100===0&&d()}t("./quote.js"),t("konami-komando")({once:!0,useCapture:!0,callback:function(){f()}});var p=t("@tweenjs/tween.js");window.TWEEN=p;var m,v,E,g,_,y,T=new THREE.Vector2,b={},M=1,C=[],k=([.4*Math.random()/20,.4*Math.random()/20,.4*Math.random()/20],.02),I=300,R=0,S=window.innerWidth>=600?5:10,j=window.innerWidth>=600?1e3:250,F=15,B=[],O=new THREE.Group,H=0,A=window.matchMedia("(prefers-color-scheme: dark)"),x=0,L=new THREE.LineBasicMaterial({color:16777215,linewidth:2}),D={twitter:["#1DA1F2","#14171A","#657786","#AAB8C2"],twitch:["#9146ff"],github:["#333","#6e5494","#c6e48b","#7bc96f","#239a3b","#196127"],evernote:["#00A82D"],stackoverflow:["#f48024","#222426","#bcbbbb"],linkedin:["#0077B5","#00A0DC","#313335","#86888A"]},q=[["#042A2B","#5EB1BF","#CDEDF6","#EF7B45","#D84727"],["#E3E7D3","#BDC2BF","#989C94","#25291C","#E6E49F"],["#EAF2E3","#61E8E1","#F25757","F2E863","F2CD60"],["#E28413","#F56416","#DD4B1A","#EF271B","#EA1744"],["#86583E","#AF2A42","#61643F","#AFBE96","#F0EEE1"],["#D44A98","#60B9CB","#FFFB53"]];e(),a(),document.getElementById("hero").appendChild(E.domElement);var P=document.getElementsByClassName("js-increment")[0];if(window.innerWidth>=600){var N=document.getElementsByClassName("content")[0];N.addEventListener("mouseover",function(t){t.target&&t.target.getAttribute("data-brand")&&c(D[t.target.getAttribute("data-brand")])})}}()},{"./quote.js":2,"@tweenjs/tween.js":4,"konami-komando":5}],2:[function(t,e,n){!function(){function e(){var t=document.getElementsByClassName("heading")[0],o=document.getElementsByClassName("description")[0],r=document.getElementsByClassName("job-title")[0];t.className="heading quote",o.className="description author",r.style.display="none";for(var a=t.innerText,s=o.innerText,u=0;u<=n.length;u++)!function(u){if(u==n.length)setTimeout(function(e){t.className="heading",o.className="description",o.innerHTML="",a.typeout(t)},1e4*u),setTimeout(function(t){s.typeout(o),r.style=""},1e4*u+2e3),i.removeEventListener("click",e);else{var c=new String(n[u].quote),h=new String(n[u].author);setTimeout(function(e){var n="“"+c+"”";n.typeout(t),o.innerHTML=""},1e4*u),setTimeout(function(t){h.typeout(o)},1e4*u+2e3)}}(u)}var n=t("../json/quotes.json"),i=document.getElementById("quotes");String.prototype.typeout=function(t){var e,n=this.split(""),i=n.slice(0);clearTimeout(e);var o="";!function r(a){var s=i.length;return a>=s?t.innerHTML=n.join("").toString():(o+=i[a],t.innerHTML=o,void(e=setTimeout(function(){r(a+1)},50)))}(0)},i.addEventListener("click",e)}()},{"../json/quotes.json":3}],3:[function(t,e,n){e.exports=[{quote:"Fairy tales are more than true — not because they tell us dragons exist, but because they tell us dragons can be beaten.",author:"G. K. Chesterton"},{quote:"Don't go through life, grow through life.",author:"Eric Butterworth"},{quote:"Wisdom is knowing what to do next, skill is knowing how to do it, and virtue is doing it.",author:"David Starr Jordan"},{quote:"Never doubt that a small group of thoughtful, committed, citizens can change the world. Indeed, it is the only thing that ever has.",author:"Margaret Mead"},{quote:"When we speak we are afraid our words will not be heard or welcomed. But when we are silent, we are still afraid. So it is better to speak.",author:"Audre Lorde"}]},{}],4:[function(t,e,n){(function(t){var i=function(){this._tweens={},this._tweensAddedDuringUpdate={}};i.prototype={getAll:function(){return Object.keys(this._tweens).map(function(t){return this._tweens[t]}.bind(this))},removeAll:function(){this._tweens={}},add:function(t){this._tweens[t.getId()]=t,this._tweensAddedDuringUpdate[t.getId()]=t},remove:function(t){delete this._tweens[t.getId()],delete this._tweensAddedDuringUpdate[t.getId()]},update:function(t,e){var n=Object.keys(this._tweens);if(0===n.length)return!1;for(t=void 0!==t?t:o.now();n.length>0;){this._tweensAddedDuringUpdate={};for(var i=0;i1?1:n,i=this._easingFunction(n);for(e in this._valuesEnd)if(void 0!==this._valuesStart[e]){var o=this._valuesStart[e]||0,r=this._valuesEnd[e];r instanceof Array?this._object[e]=this._interpolationFunction(r,i):("string"==typeof r&&(r="+"===r.charAt(0)||"-"===r.charAt(0)?o+parseFloat(r):parseFloat(r)),"number"==typeof r&&(this._object[e]=o+(r-o)*i))}if(null!==this._onUpdateCallback&&this._onUpdateCallback(this._object,n),1===n){if(this._repeat>0){isFinite(this._repeat)&&this._repeat--;for(e in this._valuesStartRepeat){if("string"==typeof this._valuesEnd[e]&&(this._valuesStartRepeat[e]=this._valuesStartRepeat[e]+parseFloat(this._valuesEnd[e])),this._yoyo){var a=this._valuesStartRepeat[e];this._valuesStartRepeat[e]=this._valuesEnd[e],this._valuesEnd[e]=a}this._valuesStart[e]=this._valuesStartRepeat[e]}return this._yoyo&&(this._reversed=!this._reversed),void 0!==this._repeatDelayTime?this._startTime=t+this._repeatDelayTime:this._startTime=t+this._delayTime,null!==this._onRepeatCallback&&this._onRepeatCallback(this._object),!0}null!==this._onCompleteCallback&&this._onCompleteCallback(this._object);for(var s=0,u=this._chainedTweens.length;s1?a(t[n],t[n-1],n-i):a(t[r],t[r+1>n?n:r+1],i-r)},Bezier:function(t,e){for(var n=0,i=t.length-1,r=Math.pow,a=o.Interpolation.Utils.Bernstein,s=0;s<=i;s++)n+=r(1-e,i-s)*r(e,s)*t[s]*a(i,s);return n},CatmullRom:function(t,e){var n=t.length-1,i=n*e,r=Math.floor(i),a=o.Interpolation.Utils.CatmullRom;return t[0]===t[n]?(e<0&&(r=Math.floor(i=n*(1+e))),a(t[(r-1+n)%n],t[r],t[(r+1)%n],t[(r+2)%n],i-r)):e<0?t[0]-(a(t[0],t[0],t[1],t[1],-i)-t[0]):e>1?t[n]-(a(t[n],t[n],t[n-1],t[n-1],i-n)-t[n]):a(t[r?r-1:0],t[r],t[n1;i--)n*=i;return t[e]=n,n}}(),CatmullRom:function(t,e,n,i,o){var r=.5*(n-t),a=.5*(i-e),s=o*o,u=o*s;return(2*e-2*n+r+a)*u+(-3*e+3*n-2*r-a)*s+r*o+e}}},function(t){"function"==typeof define&&define.amd?define([],function(){return o}):"undefined"!=typeof e&&"object"==typeof n?e.exports=o:void 0!==t&&(t.TWEEN=o)}(this)}).call(this,t("pBGvAp"))},{pBGvAp:6}],5:[function(t,e,n){var i=function(t){if("undefined"==typeof t.once&&(t.once=!0),"undefined"==typeof t.useCapture&&(t.useCapture=!0),"function"!=typeof t.callback)throw new Error("Konami: callback is not a function.");var e=!1,n=[],i=[38,38,40,40,37,39,37,39,66,65];document.addEventListener("keydown",function(o){if(!t.once||!e){var r=function(t){var e=t||window.event;return e.keyCode||e.which}(o);0==n.length&&38!=r||(n.length<10&&/37|38|39|40|65|66/.test(r)?(n.push(r),10==n.length&&JSON.stringify(n)==JSON.stringify(i)&&(t.callback(),t.once&&(e=!0))):n=[])}},t.useCapture)};e.exports=i},{}],6:[function(t,e,n){function i(){}var o=e.exports={};o.nextTick=function(){var t="undefined"!=typeof window&&window.setImmediate,e="undefined"!=typeof window&&window.postMessage&&window.addEventListener;if(t)return function(t){return window.setImmediate(t)};if(e){var n=[];return window.addEventListener("message",function(t){var e=t.source;if((e===window||null===e)&&"process-tick"===t.data&&(t.stopPropagation(),n.length>0)){var i=n.shift();i()}},!0),function(t){n.push(t),window.postMessage("process-tick","*")}}return function(t){setTimeout(t,0)}}(),o.title="browser",o.browser=!0,o.env={},o.argv=[],o.on=i,o.addListener=i,o.once=i,o.off=i,o.removeListener=i,o.removeAllListeners=i,o.emit=i,o.binding=function(t){throw new Error("process.binding is not supported")},o.cwd=function(){return"/"},o.chdir=function(t){throw new Error("process.chdir is not supported")}},{}]},{},[1]); \ No newline at end of file diff --git a/build/js/quote.js b/build/js/quote.js deleted file mode 100644 index 9fdc6f6..0000000 --- a/build/js/quote.js +++ /dev/null @@ -1,94 +0,0 @@ -(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);throw new Error("Cannot find module '"+o+"'")}var f=n[o]={exports:{}};t[o][0].call(f.exports,function(e){var n=t[o][1][e];return s(n?n:e)},f,f.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o=len){ - return targetElem.innerHTML = str.join('').toString();// you can use your selectors - } - ll = ll + strCopy[start]; - targetElem.innerHTML = ll; // you can use your selectors - timer = setTimeout(function(){ - shuffle(start+1); - }, 50); - })(0); - } - - function triggerQuoteAnimation() { - var heading = document.getElementsByClassName('heading')[0]; - var description = document.getElementsByClassName('description')[0]; - var jobTitle = document.getElementsByClassName("job-title")[0]; - heading.className = 'heading quote'; - description.className = 'description author'; - jobTitle.style.display = 'none'; - - var oHeading = heading.innerText; - var oDescription = description.innerText; - for (var i=0; i<=quotes.length; i++) { - (function(i) { - if (i == quotes.length) { - setTimeout(function(e) { - heading.className = 'heading'; - description.className = 'description'; - description.innerHTML = ''; - oHeading.typeout(heading); - }, 10000*i); - setTimeout(function(e) { - oDescription.typeout(description); - jobTitle.style = ''; - }, 10000*i+2000); - quoteTrigger.removeEventListener('click', triggerQuoteAnimation); - } else { - var quote = new String(quotes[i].quote); - var author = new String(quotes[i].author); - setTimeout(function(e) { - var moddedQuote = '“' + quote + '”'; - moddedQuote.typeout(heading); - description.innerHTML = ''; - }, 10000*i); - setTimeout(function(e) { - author.typeout(description); - }, 10000*i+2000); - } - })(i); - } - } - - quoteTrigger.addEventListener('click', triggerQuoteAnimation); -})(); -},{"../json/quotes.json":2}],2:[function(require,module,exports){ -module.exports=[ - { - "quote" : "Fairy tales are more than true — not because they tell us dragons exist, but because they tell us dragons can be beaten.", - "author": "G. K. Chesterton" - }, - { - "quote" : "Don't go through life, grow through life.", - "author": "Eric Butterworth" - }, - { - "quote" : "Wisdom is knowing what to do next, skill is knowing how to do it, and virtue is doing it.", - "author": "David Starr Jordan" - }, - { - "quote": "Never doubt that a small group of thoughtful, committed, citizens can change the world. Indeed, it is the only thing that ever has.", - "author": "Margaret Mead" - }, - { - "quote": "When we speak we are afraid our words will not be heard or welcomed. But when we are silent, we are still afraid. So it is better to speak.", - "author": "Audre Lorde" - } -] - - -},{}]},{},[1]) \ No newline at end of file diff --git a/build/js/quote.min.js b/build/js/quote.min.js deleted file mode 100644 index f7d8720..0000000 --- a/build/js/quote.min.js +++ /dev/null @@ -1 +0,0 @@ -!function e(t,n,o){function r(u,a){if(!n[u]){if(!t[u]){var s="function"==typeof require&&require;if(!a&&s)return s(u,!0);if(i)return i(u,!0);throw new Error("Cannot find module '"+u+"'")}var l=n[u]={exports:{}};t[u][0].call(l.exports,function(e){var n=t[u][1][e];return r(n?n:e)},l,l.exports,e,t,n,o)}return n[u].exports}for(var i="function"==typeof require&&require,u=0;u=a?e.innerHTML=n.join("").toString():(r+=o[u],e.innerHTML=r,void(t=setTimeout(function(){i(u+1)},50)))}(0)},o.addEventListener("click",t)}()},{"../json/quotes.json":2}],2:[function(e,t,n){t.exports=[{quote:"Fairy tales are more than true — not because they tell us dragons exist, but because they tell us dragons can be beaten.",author:"G. K. Chesterton"},{quote:"Don't go through life, grow through life.",author:"Eric Butterworth"},{quote:"Wisdom is knowing what to do next, skill is knowing how to do it, and virtue is doing it.",author:"David Starr Jordan"},{quote:"Never doubt that a small group of thoughtful, committed, citizens can change the world. Indeed, it is the only thing that ever has.",author:"Margaret Mead"},{quote:"When we speak we are afraid our words will not be heard or welcomed. But when we are silent, we are still afraid. So it is better to speak.",author:"Audre Lorde"}]},{}]},{},[1]); \ No newline at end of file diff --git a/favicon-16x16.png b/favicon-16x16.png deleted file mode 100644 index 2a1b907..0000000 Binary files a/favicon-16x16.png and /dev/null differ diff --git a/favicon-32x32.png b/favicon-32x32.png deleted file mode 100644 index 002773c..0000000 Binary files a/favicon-32x32.png and /dev/null differ diff --git a/favicon.ico b/favicon.ico deleted file mode 100644 index 4e276fc..0000000 Binary files a/favicon.ico and /dev/null differ diff --git a/index.html b/index.html index 80aa996..719b580 100644 --- a/index.html +++ b/index.html @@ -1,64 +1,17 @@ - + - - - Augustus Yuan. Web Developer. Quote lover. Lifelong Learner. - - - - - - - - - - - - - -
-
- -
    - - -
-
-
-
-
- Augustus profile picture -

Augustus Yuan

-

Software Engineer at HeyGen

-

Web Developer. Quote Lover. Lifelong learner.

- - -
- - - - + + + + Augustus Yuan | Personal Site + + + + +
+ + diff --git a/js/main.js b/js/main.js deleted file mode 100644 index 968d3c0..0000000 --- a/js/main.js +++ /dev/null @@ -1,368 +0,0 @@ -(function() { - 'use strict'; - require('./quote.js'); - require("konami-komando")({ - once: true, - useCapture: true, - callback: function() { - blowUpCubes(); - } - }); - var TWEEN = require("@tweenjs/tween.js"); - window.TWEEN = TWEEN; - - var camera, scene, renderer; - - var raycaster; - var mouse = new THREE.Vector2(), INTERSECTED = {}; - var multiplier = 1; - var objects = []; - var rotationSpeed = [(Math.random() * 0.4) / 20, (Math.random() * 0.4) / 20, (Math.random() * 0.4) / 20]; - var PIVOT_SPEED = 0.02; - var RADIUS = 300; - var theta = 0; - var CUBE_SIZE = window.innerWidth >= 600 ? 5 : 10; - var NUM_OF_CUBES = window.innerWidth >= 600 ? 1000 : 250; - var SATISFIABLE_CUBE_SCORE = 15; - var filterCoordinates = []; - var pivot = new THREE.Group(); - var themeIndex = 0; - - var darkModeMedia = window.matchMedia('(prefers-color-scheme: dark)'); - - var cubeScore = 0; - var lineMaterial = new THREE.LineBasicMaterial({ - color: 0xffffff, - linewidth: 2 - }); - - var pivotInterval, pivotTimeout; - - var socialThemes = { - "twitter": ["#1DA1F2", "#14171A", "#657786", "#AAB8C2"], - "twitch": ["#9146ff"], - "github": ["#333", "#6e5494", "#c6e48b", "#7bc96f", "#239a3b", "#196127"], - "evernote": ['#00A82D'], - "stackoverflow": ["#f48024", "#222426", "#bcbbbb"], - "linkedin": ["#0077B5", "#00A0DC", "#313335", "#86888A"] - } - - var themes = [ - ["#042A2B", "#5EB1BF", "#CDEDF6", "#EF7B45", "#D84727"], - ["#E3E7D3", "#BDC2BF", "#989C94", "#25291C", "#E6E49F"], - ["#EAF2E3", "#61E8E1", "#F25757", "F2E863", "F2CD60"], - ['#E28413', '#F56416', '#DD4B1A', '#EF271B', '#EA1744'], - ['#86583E', '#AF2A42', '#61643F', '#AFBE96', '#F0EEE1'], - ['#D44A98', '#60B9CB', '#FFFB53'], //cmyk - ]; - - init(); - animate(); - document.getElementById("hero").appendChild(renderer.domElement); - var keepScoreElement = document.getElementsByClassName('js-increment')[0]; - - if (window.innerWidth >= 600) { - var themeHoversItemContainer = document.getElementsByClassName('content')[0]; - themeHoversItemContainer.addEventListener('mouseover', function(e) { - if (e.target && e.target.getAttribute('data-brand')) { - themifyCubes(socialThemes[e.target.getAttribute('data-brand')]); - } - }); - } - - function init() { - camera = new THREE.PerspectiveCamera( 70, window.innerWidth / window.innerHeight, 1, 10000 ); - camera.position.y = 300; - camera.position.z = window.innerWidth >= 600 ? 500 : 200; - - scene = new THREE.Scene(); - scene.add(pivot); - - raycaster = new THREE.Raycaster(); - mouse = new THREE.Vector2(); - - renderer = new THREE.WebGLRenderer(); - renderer.setClearColor(darkModeMedia.matches ? "black" : "white"); - renderer.setPixelRatio( window.devicePixelRatio ); - renderer.setSize( window.innerWidth, window.innerHeight ); - - var geometry = new THREE.BoxGeometry( CUBE_SIZE, CUBE_SIZE, CUBE_SIZE ); - geometry.colorsNeedUpdate = true; - - for (var i = 0; i < NUM_OF_CUBES; i++) { - var randomColor = Math.random() * 0xffffff; - // generate random coordinates that are not already occupied yet - var coordinates = generateRandomCoords(filterCoordinates); - objects[i] = new THREE.Mesh( geometry, new THREE.MeshBasicMaterial( { color: new THREE.Color(randomColor), opacity: 0.6, transparent: true, depthWrite: false } ) ); - objects[i].position.set(coordinates.x, coordinates.y, coordinates.z); - - // add to filter so we do not generate conflicting coordinates again - filterCoordinates.push(coordinates); - - // modify rotation - objects[i].rotation.x = Math.random() * 2 * Math.PI; - objects[i].rotation.y = Math.random() * 2 * Math.PI; - pivot.add( objects[i] ); - - var edges = new THREE.EdgesGeometry( geometry ); - var line = new THREE.LineSegments(edges, lineMaterial); - objects[i].add(line); - } - - document.addEventListener( 'keyup', onKeyUp, false ); - document.addEventListener('mousemove', onDocumentMouseMove, false); - - if (window.DeviceOrientationEvent) { - window.addEventListener( 'deviceorientation', onDeviceOrientation, false ); - } - window.addEventListener( 'resize', onWindowResize, false ); - - // Detect dark mode only supported in Safari 12.1 - if (darkModeMedia.matches) { - setColorScheme({ darkMode: true, shouldTransition: false }); - } - darkModeMedia.addListener(function(e) { - var colorSchemeOptions = { - darkMode: darkModeMedia.matches, - shouldTransition: true, - } - setColorScheme(colorSchemeOptions); - //darkModeMedia.matches ? darkMode() : lightMode(); - }); - - if (window.innerWidth > 600 || !window.DeviceOrientationEvent) { - if (pivotInterval) { - clearInterval(pivotInterval); - } - if (pivotTimeout) { - clearTimeout(pivotTimeout); - } - // set time shift - pivotInterval = setInterval(function() { - PIVOT_SPEED = 0.2; - var pivotTimeout = setTimeout(function() { - PIVOT_SPEED = 0.02; - }, 750) - }, 12000); - } - } - - function onWindowResize() { - if (pivotInterval) { - clearInterval(pivotInterval); - } - if (pivotTimeout) { - clearTimeout(pivotTimeout); - } - - camera.aspect = window.innerWidth / window.innerHeight; - camera.updateProjectionMatrix(); - - renderer.setSize( window.innerWidth, window.innerHeight ); - renderer.render( scene, camera ); - } - - function onKeyUp(e) { - themeIndex = (themeIndex + 1) % themes.length; - if (e.key.includes('Arrow')) { - themifyCubes(themes[themeIndex]); - } - } - - function onDeviceOrientation( event ) { - // set camera to change its view based on gyroscope - // NOTE: adding 100 to beta starts the phone as if it were vertical - var vectorAngle = new THREE.Vector3( - RADIUS * Math.sin(THREE.Math.degToRad( event.alpha ))*-1, - RADIUS * Math.sin(THREE.Math.degToRad( event.beta + 100 ))*-1, - scene.position.z - ) - camera.lookAt(vectorAngle); - - raycaster.setFromCamera( mouse, camera ); - renderer.render( scene, camera ); - } - - function onDocumentMouseMove(event) { - event.preventDefault(); - mouse.x = event.clientX / window.innerWidth * 2 - 1; - mouse.y = -(event.clientY / window.innerHeight) * 2 + 1; - - // if user hovers over specific cube, TWEEN scale to make it pop - raycaster.setFromCamera(mouse, camera); - var intersects = raycaster.intersectObjects(objects); - - // check we have intersects and that the uuid of the object is not already tweening - if (intersects.length > 0) { - if (!INTERSECTED[intersects[0].object.uuid]) { - INTERSECTED[intersects[0].object.uuid] = intersects[0].object; - var scaleTween = new TWEEN.Tween(intersects[0].object.scale) - .to({ x: 3, y: 3, z: 3 }, 500) - .easing(TWEEN.Easing.Elastic.Out); - var rotationTween = new TWEEN.Tween(intersects[0].object.rotation) - .to({ x: Math.random(), y: Math.random(), z: Math.random() }, 500) - .easing(TWEEN.Easing.Elastic.Out) - var shrinkTween = new TWEEN.Tween(intersects[0].object.scale) - .to({ x: 1, y: 1, z: 1 }, 500) - .delay(1000) - .easing(TWEEN.Easing.Elastic.Out) - .onComplete(function(tween) { - var uuid = Object.keys(INTERSECTED).shift(); - delete INTERSECTED[uuid]; - }); - scaleTween.chain(shrinkTween).start(); - rotationTween.start(); - incrementScore(); - } - } - } - - function animate() { - requestAnimationFrame( animate ); - TWEEN.update(); - render(); - } - - function render() { - // in order to prevent the theta from forever growing which could hit Number.MAX_SAFE_INTEGER, - // go reverse and interchange - if (multiplier > 0 && theta >= 100) { - multiplier = -1; - } else if (multiplier < 0 && theta <= 0) { - multiplier = 1; - } - theta += PIVOT_SPEED * multiplier; - - pivot.rotation.set( - Math.sin( THREE.Math.degToRad( theta )), - Math.sin( THREE.Math.degToRad( theta )), - Math.sin( THREE.Math.degToRad( theta )) - ); - - raycaster.setFromCamera( mouse, camera ); - renderer.render( scene, camera ); - } - - // generate random coordinates based on page and size of cubes - // TODO: handle filtering of coordinates - function generateRandomCoords(filterCoordinates) { - var coords = { - x: (Math.random() * 800 - 200), - y: (Math.random() * 800 - 200), - z: (Math.random() * 800 - 200) - }; - - return coords; - } - - // takes in an array of hex colors and applies the theme equally to the cubes - function themifyCubes(theme) { - if (!theme) { - for (var i = 0; i < objects.length; i++) { - var randomColor = Math.random() * 0xffffff; - objects[i].material.color.set(new THREE.Color(randomColor)); - } - } else { - for (var i = 0; i < objects.length; i++) { - var hexColor = parseInt(theme[i % theme.length].replace("#", "0x"), 16); - objects[i].material.color.set(new THREE.Color(hexColor)); - } - } - } - - /** - * Sets the color scheme - * options: { darkMode: boolean, shouldTransition: boolean } - */ - function setColorScheme(options) { - var whiteClearColor = new THREE.Color("white"); - var darkClearColor = new THREE.Color("black"); - var firstClearColor = options.darkMode ? whiteClearColor : darkClearColor; - var transitionedClearColor = options.darkMode ? darkClearColor : whiteClearColor; - if (options.shouldTransition) { - var colorModeTween = new TWEEN.Tween(firstClearColor) - .to(transitionedClearColor, 500).onUpdate(function() { - renderer.setClearColor(firstClearColor); - }).start(); - } else { - renderer.setClearColor(transitionedClearColor); - } - if (options.darkMode) { - document.body.classList.add("dark-mode"); - } else { - document.body.classList.remove("dark-mode"); - } - lineMaterial = new THREE.LineBasicMaterial({ - color: options.darkMode ? 0x000000 : 0xffffff, - linewidth: 2 - }); - var geometry = new THREE.BoxGeometry( CUBE_SIZE, CUBE_SIZE, CUBE_SIZE ); - geometry.colorsNeedUpdate = true; - var edges = new THREE.EdgesGeometry( geometry ); - for (var i = 0; i < objects.length; i++) { - var line = new THREE.LineSegments(edges, lineMaterial); - objects[i].add(line); - } - render(); - } - - // flicker cubes through all the themes twice! :) - function flickerCubes() { - var ran = false; - var i = 0; - var index = 0; - while (i++ < themes.length) { - var theme = themes[i]; - if (i === themes.length - 1 && !ran) { - ran = true; - i = 0; - } else if (i === themes.length - 1) { - theme = false; - } - (function(i) { - setTimeout(function() { - themifyCubes(theme); - }, index++ * 200); - })(i); - } - } - - // Handy function to handle logarithmic function - function getBaseLog(x, y) { - return Math.log(y) / Math.log(x); - } - - // Blow up all the cubes in logarithmic fashion so as time goes on, we blow up more - function blowUpCubes() { - var shrinkTweens = []; - for (var i = 0; i < objects.length; i+=2) { - var delay = Math.floor(getBaseLog(2, i) * 200); - var scaleTween = new TWEEN.Tween(objects[i].scale) - .delay(delay) - .to({ x: 3, y: 3, z: 3 }, 500) - .easing(TWEEN.Easing.Elastic.Out).onComplete(function() { - shrinkTween.start(); - }); - var rotationTween = new TWEEN.Tween(objects[i].rotation) - .delay(delay) - .to({ x: Math.random(), y: Math.random(), z: Math.random() }, 500) - .easing(TWEEN.Easing.Elastic.Out) - var shrinkTween = new TWEEN.Tween(objects[i].scale) - .delay(Math.floor(getBaseLog(2, Math.floor(objects.length / 2)) * 200)) - .to({ x: 1, y: 1, z: 1 }, 500) - .easing(TWEEN.Easing.Elastic.Out); - scaleTween.chain(shrinkTween).start(); - rotationTween.start(); - } - } - - function incrementScore() { - cubeScore++; - keepScoreElement.innerText = cubeScore; - if (cubeScore >= SATISFIABLE_CUBE_SCORE && document.getElementsByClassName('js-score-hidden').length > 0) { - document.getElementsByClassName('js-score-hidden')[0].classList.remove('js-score-hidden'); - } else if (cubeScore % 100 === 0) { - flickerCubes(); - } - } -})(); diff --git a/js/quote.js b/js/quote.js deleted file mode 100644 index 73ed10e..0000000 --- a/js/quote.js +++ /dev/null @@ -1,67 +0,0 @@ -(function() { - var quotes = require('../json/quotes.json'); - var quoteTrigger = document.getElementById('quotes'); - - String.prototype.typeout = function(targetElem) { - var timer; - var str = this.split(''); - var strCopy = str.slice(0); - clearTimeout(timer); - var ll = ''; - (function shuffle(start){ - // This code is run options.fps times per second - // and updates the contents of the page element - var i, len = strCopy.length; - if(start>=len){ - return targetElem.innerHTML = str.join('').toString();// you can use your selectors - } - ll = ll + strCopy[start]; - targetElem.innerHTML = ll; // you can use your selectors - timer = setTimeout(function(){ - shuffle(start+1); - }, 50); - })(0); - } - - function triggerQuoteAnimation() { - var heading = document.getElementsByClassName('heading')[0]; - var description = document.getElementsByClassName('description')[0]; - var jobTitle = document.getElementsByClassName("job-title")[0]; - heading.className = 'heading quote'; - description.className = 'description author'; - jobTitle.style.display = 'none'; - - var oHeading = heading.innerText; - var oDescription = description.innerText; - for (var i=0; i<=quotes.length; i++) { - (function(i) { - if (i == quotes.length) { - setTimeout(function(e) { - heading.className = 'heading'; - description.className = 'description'; - description.innerHTML = ''; - oHeading.typeout(heading); - }, 10000*i); - setTimeout(function(e) { - oDescription.typeout(description); - jobTitle.style = ''; - }, 10000*i+2000); - quoteTrigger.removeEventListener('click', triggerQuoteAnimation); - } else { - var quote = new String(quotes[i].quote); - var author = new String(quotes[i].author); - setTimeout(function(e) { - var moddedQuote = '“' + quote + '”'; - moddedQuote.typeout(heading); - description.innerHTML = ''; - }, 10000*i); - setTimeout(function(e) { - author.typeout(description); - }, 10000*i+2000); - } - })(i); - } - } - - quoteTrigger.addEventListener('click', triggerQuoteAnimation); -})(); \ No newline at end of file diff --git a/json/quotes.json b/json/quotes.json deleted file mode 100644 index 23f1c80..0000000 --- a/json/quotes.json +++ /dev/null @@ -1,23 +0,0 @@ -[ - { - "quote" : "Fairy tales are more than true — not because they tell us dragons exist, but because they tell us dragons can be beaten.", - "author": "G. K. Chesterton" - }, - { - "quote" : "Don't go through life, grow through life.", - "author": "Eric Butterworth" - }, - { - "quote" : "Wisdom is knowing what to do next, skill is knowing how to do it, and virtue is doing it.", - "author": "David Starr Jordan" - }, - { - "quote": "Never doubt that a small group of thoughtful, committed, citizens can change the world. Indeed, it is the only thing that ever has.", - "author": "Margaret Mead" - }, - { - "quote": "When we speak we are afraid our words will not be heard or welcomed. But when we are silent, we are still afraid. So it is better to speak.", - "author": "Audre Lorde" - } -] - diff --git a/llms.txt b/llms.txt deleted file mode 100644 index 7badd91..0000000 --- a/llms.txt +++ /dev/null @@ -1,25 +0,0 @@ -# llms.txt -# Instructions for Large Language Models on how to handle this site’s content. -# This file is non-standard and may not be respected by all crawlers. - -# General policy: -# Options: allow / disallow / limited -policy: allow - -# Attribution: -# If using excerpts, always attribute content to this site. -attribution: required - -# Commercial use: -# Disallow training or fine-tuning on this content for commercial purposes. -commercial-use: disallow - -# Research use: -# Allow non-commercial, research-based usage. -research-use: allow - -# Contact for permissions: -contact: hello@augustusyuan.com - -# Last updated: -last-modified: 2025-08-23 \ No newline at end of file diff --git a/package.json b/package.json index 21069f3..5e35df4 100644 --- a/package.json +++ b/package.json @@ -1,42 +1,21 @@ { "name": "augbog.github.io", + "private": true, "version": "1.0.0", - "description": "Augustus Yuan's personal website", - "repository": "augbog.github.io", - "author": "Augustus Yuan", + "type": "module", "scripts": { - "build": "gulp svgstore sass scripts", - "dev": "gulp" - }, - "devDependencies": { - "autoprefixer": "^6.4.0", - "babel-eslint": "^4.1.6", - "beepbeep": "~1.2.0", - "browser-sync": "^2.7.1", - "colors": "~1.1.2", - "eslint": "^6.7.2", - "eslint-plugin-react": "^3.11.3", - "gulp": "^3.8.11", - "gulp-browserify": "^0.5.1", - "gulp-eslint": "^1.1.1", - "gulp-inject": "^4.0.0", - "gulp-jsonlint": "^1.1.2", - "gulp-minify-css": "^1.1.1", - "gulp-notify": "^2.2.0", - "gulp-plumber": "~1.0.1", - "gulp-postcss": "^6.1.1", - "gulp-rename": "^1.2.2", - "gulp-replace": "^0.5.4", - "gulp-sass": "^2.1.1", - "gulp-sourcemaps": "^1.6.0", - "gulp-svgmin": "^1.2.2", - "gulp-svgstore": "^6.0.0", - "gulp-uglify": "^1.2.0", - "merge-stream": "^1.0.1", - "path": "^0.11.14" + "dev": "vite", + "build": "vite build", + "preview": "vite preview" }, "dependencies": { - "@tweenjs/tween.js": "^17.2.0", - "konami-komando": "^1.0.1" + "react": "^19.1.1", + "react-dom": "^19.1.1" + }, + "devDependencies": { + "autoprefixer": "^10.4.20", + "postcss": "^8.5.6", + "tailwindcss": "^3.4.17", + "vite": "^7.1.3" } } diff --git a/postcss.config.js b/postcss.config.js new file mode 100644 index 0000000..2aa7205 --- /dev/null +++ b/postcss.config.js @@ -0,0 +1,6 @@ +export default { + plugins: { + tailwindcss: {}, + autoprefixer: {}, + }, +}; diff --git a/public/CNAME b/public/CNAME new file mode 100644 index 0000000..9a6c58e --- /dev/null +++ b/public/CNAME @@ -0,0 +1 @@ +augustusyuan.com \ No newline at end of file diff --git a/quotes.html b/quotes.html deleted file mode 100644 index 7ea033e..0000000 --- a/quotes.html +++ /dev/null @@ -1,17 +0,0 @@ - - - - - Augustus Yuan - - - - -
- -

-

-
- - - \ No newline at end of file diff --git a/sass/mixins/_breakpoint.scss b/sass/mixins/_breakpoint.scss deleted file mode 100644 index f10e9d2..0000000 --- a/sass/mixins/_breakpoint.scss +++ /dev/null @@ -1,10 +0,0 @@ -/** - * Breakpoint mixin that will apply specific styles depending on - * screen size - * - * @param: target screen size - **/ - -@mixin breakpoint($size) { - @media only screen and (max-width: $size + px) { @content; } -} \ No newline at end of file diff --git a/sass/modules/_extras.scss b/sass/modules/_extras.scss deleted file mode 100644 index 6229810..0000000 --- a/sass/modules/_extras.scss +++ /dev/null @@ -1,37 +0,0 @@ -.animate-link { - border-bottom: 0.5px solid transparent; - &:hover { - cursor: pointer; - transition: border-color 0.5s ease-in 0s; - border-color: rgba(0,0,0,0.2); - } -} - -body { - transition: all 0.5s ease-in 0s; -} - -@mixin darkMode { - color: white !important; - font-weight: 800 !important; - - .github, .mail-icon { - use { - fill: white !important; - } - } - - .content { - background: transparent !important; - } - - .job-title, .description, .email { - font-weight: 400 !important; - } -} - -@media (prefers-color-scheme: dark) { - body { - @include darkMode(); - } -} \ No newline at end of file diff --git a/sass/modules/_header.scss b/sass/modules/_header.scss deleted file mode 100644 index 45c22c6..0000000 --- a/sass/modules/_header.scss +++ /dev/null @@ -1,63 +0,0 @@ -/** - * Header styles - **/ - - header { - font-family: "Helvetica Neue", helvetica, arial, sans-serif; - -webkit-font-smoothing: antialiased; - text-rendering: optimizeLegibility; - font-weight: 200; - - position: absolute; - top: 0; - width: 100%; - height: auto; - z-index: 3; - - @include breakpoint(600) { - text-align: center; - } - - .header-container { - display: flex; - - margin: 0px 20px; - } - - .left-align { - align-self: flex-start; - } - - .right-align { - margin-left: auto; - } - - .secondary-nav { - line-height: 22px; - } - - .mail-icon { - width: 15px; - height: 22px; // set the height so it vertically aligns - vertical-align: bottom; - } - - li { - display: inline-block; - height: auto; - - margin: 0px 20px; - - &:first-child { - margin-left: 0; - } - - &:last-child { - margin-right: 0; - } - } - - .profile { - border-radius: 50%; - } -} \ No newline at end of file diff --git a/sass/modules/_hero.scss b/sass/modules/_hero.scss deleted file mode 100644 index 4668def..0000000 --- a/sass/modules/_hero.scss +++ /dev/null @@ -1,126 +0,0 @@ -/** - * Hero styles - **/ - -.hero { - -webkit-font-smoothing: antialiased; - text-rendering: optimizeLegibility; - font-family: "Helvetica Neue", helvetica, arial, sans-serif; - position: relative; - overflow: hidden; - - .content { - position: fixed; - text-align: center; - width: 100%; - top: 50%; - left: 50%; - transform: translate(-50%, -50%); - background: rgba(255,255,255,0.7); - padding: 20px 0px; - } - - .heading { - max-width: 80%; - margin-left: auto; - margin-right: auto; - font-size: 36px; - font-weight: 400; - letter-spacing: -0.5px; - margin-bottom: 5px; - - &.quote { - font-size: 26px; - max-width: 60%; - - @include breakpoint(600) { - font-size: 24px; - max-width: 80%; - } - } - } - - .job-title { - font-size: 20px; - font-weight: 200; - margin-bottom: 10px; - vertical-align: middle; - } - - .description { - font-size: 20px; - font-weight: 200; - margin: 0 0 20px 0; - } - - svg { - width: inherit; - height: inherit; - } - - .icon { - display: inline-block; - width: 20px; - height: 20px; - margin: 0px 10px; - - &:hover, &:focus { - transition: transform 0.1s ease-out 0s; - transform: scale(1.2); - } - - @include breakpoint(600) { - width: 30px; - height: 30px; - } - } - - .evernote { - display: inline-block; - width: 25px; - height: 25px; - fill: #666; - vertical-align: bottom; - - &:hover, &:focus { - transition: transform 0.1s ease-out 0s; - transform: scale(1.2); - } - } - - .twitch { - display: inline-block; - width: 25px; - height: 25px; - fill: #9146ff; - vertical-align: bottom; - - &:hover, &:focus { - transition: transform 0.1s ease-out 0s; - transform: scale(1.2); - } - } - - .twitter { - fill: #5EA9DD; - } - - .linkedin { - fill: #0077B5; - } -} - -.profile { - width: 100px; - border-radius: 50%; -} - -.score { - font-family: monospace; - font-size: 30px; - font-weight: 800; -} - -.js-score-hidden { - display: none; -} \ No newline at end of file diff --git a/sass/modules/_reset.scss b/sass/modules/_reset.scss deleted file mode 100644 index 21bc1d4..0000000 --- a/sass/modules/_reset.scss +++ /dev/null @@ -1,22 +0,0 @@ -/** - * Reset styles on DOM elements so we can properly - * style them - **/ - -body, h1, h2 { - margin: 0; -} - -ul { - padding: 0; -} - -li { - list-style-type: none; -} - -a, a:link, a:visited { - color: inherit; - text-decoration: none; - border-bottom: 1px solid transparent; -} \ No newline at end of file diff --git a/sass/style.scss b/sass/style.scss deleted file mode 100644 index 949a252..0000000 --- a/sass/style.scss +++ /dev/null @@ -1,14 +0,0 @@ -/** - * Main Stylesheet file for augbog.github.io - */ - -// Mixins -@import "mixins/breakpoint"; - -// Modular styles -@import "modules/header"; -@import "modules/hero"; - -// Other styles -@import "modules/reset"; -@import "modules/extras"; \ No newline at end of file diff --git a/site.webmanifest b/site.webmanifest deleted file mode 100644 index 45dc8a2..0000000 --- a/site.webmanifest +++ /dev/null @@ -1 +0,0 @@ -{"name":"","short_name":"","icons":[{"src":"/android-chrome-192x192.png","sizes":"192x192","type":"image/png"},{"src":"/android-chrome-512x512.png","sizes":"512x512","type":"image/png"}],"theme_color":"#ffffff","background_color":"#ffffff","display":"standalone"} \ No newline at end of file diff --git a/src/App.js b/src/App.js new file mode 100644 index 0000000..d00ff33 --- /dev/null +++ b/src/App.js @@ -0,0 +1,117 @@ +import React from 'https://esm.sh/react@19.1.1'; + +const { useEffect, useRef } = React; +const h = React.createElement; + +const socialLinks = [ + { label: 'Twitter', href: 'https://mobile.twitter.com/augburto' }, + { label: 'GitHub', href: 'https://github.com/augbog' }, + { label: 'LinkedIn', href: 'https://www.linkedin.com/in/augustusyuan' }, + { label: 'Stack Overflow', href: 'https://stackoverflow.com/users/1168661/aug' }, +]; + +function AnimatedPatternCanvas() { + const canvasRef = useRef(null); + + useEffect(() => { + const canvas = canvasRef.current; + const context = canvas?.getContext('2d'); + + if (!canvas || !context) { + return undefined; + } + + let animationFrameId; + let width = window.innerWidth; + let height = window.innerHeight; + const pixelRatio = Math.min(window.devicePixelRatio || 1, 2); + + const setCanvasSize = () => { + width = window.innerWidth; + height = window.innerHeight; + canvas.width = Math.floor(width * pixelRatio); + canvas.height = Math.floor(height * pixelRatio); + canvas.style.width = `${width}px`; + canvas.style.height = `${height}px`; + context.setTransform(pixelRatio, 0, 0, pixelRatio, 0, 0); + }; + + const drawPattern = (time) => { + const t = time * 0.001; + const spacing = 48; + + context.clearRect(0, 0, width, height); + + for (let x = -spacing; x < width + spacing; x += spacing) { + for (let y = -spacing; y < height + spacing; y += spacing) { + const waveX = Math.sin((x * 0.012) + t * 1.2); + const waveY = Math.cos((y * 0.012) - t * 0.9); + const offset = (waveX + waveY) * 8; + const radius = 1.5 + ((waveX + 1) * 2.2); + const alpha = 0.14 + ((waveY + 1) / 2) * 0.18; + + context.beginPath(); + context.fillStyle = `rgba(34, 211, 238, ${alpha.toFixed(3)})`; + context.arc(x + offset, y - offset, radius, 0, Math.PI * 2); + context.fill(); + } + } + + animationFrameId = window.requestAnimationFrame(drawPattern); + }; + + setCanvasSize(); + animationFrameId = window.requestAnimationFrame(drawPattern); + window.addEventListener('resize', setCanvasSize); + + return () => { + window.cancelAnimationFrame(animationFrameId); + window.removeEventListener('resize', setCanvasSize); + }; + }, []); + + return h('canvas', { ref: canvasRef, className: 'animated-pattern', 'aria-hidden': 'true' }); +} + +export default function App() { + return h( + 'main', + { className: 'site-shell' }, + h(AnimatedPatternCanvas), + h( + 'section', + { className: 'hero-card' }, + h('p', { className: 'kicker' }, 'Augustus Yuan'), + h('h1', null, 'Augustus Yuan'), + h( + 'p', + { className: 'role' }, + 'Software Engineer at ', + h( + 'a', + { href: 'https://heygen.com', target: '_blank', rel: 'noreferrer' }, + 'HeyGen', + ), + ), + h( + 'nav', + { 'aria-label': 'Social links' }, + h( + 'ul', + { className: 'social-list' }, + ...socialLinks.map((link) => + h( + 'li', + { key: link.label }, + h( + 'a', + { href: link.href, target: '_blank', rel: 'noreferrer' }, + link.label, + ), + ), + ), + ), + ), + ), + ); +} diff --git a/src/index.css b/src/index.css new file mode 100644 index 0000000..44e9f95 --- /dev/null +++ b/src/index.css @@ -0,0 +1,106 @@ +@tailwind base; +@tailwind components; +@tailwind utilities; + +:root { + font-family: Inter, system-ui, -apple-system, BlinkMacSystemFont, 'Segoe UI', sans-serif; + color: #e2e8f0; + background: #020617; +} + +* { + box-sizing: border-box; +} + +body { + margin: 0; +} + +.site-shell { + position: relative; + min-height: 100vh; + display: grid; + place-items: center; + overflow: hidden; + background: radial-gradient(circle at top, #0f172a 0%, #020617 65%); +} + +.animated-pattern { + position: absolute; + inset: 0; + width: 100%; + height: 100%; +} + +.hero-card { + position: relative; + z-index: 1; + width: min(90vw, 720px); + border: 1px solid rgba(148, 163, 184, 0.25); + border-radius: 24px; + background: rgba(15, 23, 42, 0.75); + backdrop-filter: blur(8px); + padding: 2.25rem; + text-align: center; + box-shadow: 0 20px 70px rgba(2, 6, 23, 0.6); +} + +.kicker { + margin: 0; + color: #67e8f9; + font-weight: 600; + letter-spacing: 0.16em; + text-transform: uppercase; + font-size: 0.75rem; +} + +.hero-card h1 { + margin: 0.5rem 0 0; + color: #f8fafc; + font-size: clamp(2rem, 5vw, 3.25rem); + line-height: 1.1; +} + +.role { + margin: 0.85rem 0 0; + font-size: clamp(1rem, 2vw, 1.25rem); + color: #cbd5e1; +} + +.role a { + color: #22d3ee; + text-decoration: none; + border-bottom: 1px solid transparent; + transition: border-color 0.2s ease; +} + +.role a:hover { + border-color: #22d3ee; +} + +.social-list { + margin: 2rem 0 0; + padding: 0; + list-style: none; + display: flex; + flex-wrap: wrap; + justify-content: center; + gap: 0.75rem; +} + +.social-list a { + display: inline-block; + border: 1px solid rgba(148, 163, 184, 0.35); + border-radius: 999px; + padding: 0.5rem 0.9rem; + color: #e2e8f0; + text-decoration: none; + font-weight: 500; + transition: all 0.2s ease; +} + +.social-list a:hover { + border-color: rgba(34, 211, 238, 0.9); + color: #67e8f9; + transform: translateY(-1px); +} diff --git a/src/main.js b/src/main.js new file mode 100644 index 0000000..781c18d --- /dev/null +++ b/src/main.js @@ -0,0 +1,5 @@ +import React from 'https://esm.sh/react@19.1.1'; +import { createRoot } from 'https://esm.sh/react-dom@19.1.1/client'; +import App from './App.js'; + +createRoot(document.getElementById('root')).render(React.createElement(App)); diff --git a/svg/codepen.svg b/svg/codepen.svg deleted file mode 100644 index 8c452bb..0000000 --- a/svg/codepen.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/svg/evernote.svg b/svg/evernote.svg deleted file mode 100644 index 4b0d304..0000000 --- a/svg/evernote.svg +++ /dev/null @@ -1 +0,0 @@ -Evernote icon \ No newline at end of file diff --git a/svg/github.svg b/svg/github.svg deleted file mode 100644 index 48893ba..0000000 --- a/svg/github.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/svg/jsfiddle.svg b/svg/jsfiddle.svg deleted file mode 100644 index bb9e353..0000000 --- a/svg/jsfiddle.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/svg/linkedin.svg b/svg/linkedin.svg deleted file mode 100644 index 349c0b3..0000000 --- a/svg/linkedin.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/svg/mail.svg b/svg/mail.svg deleted file mode 100644 index 6c184cb..0000000 --- a/svg/mail.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/svg/stackoverflow.svg b/svg/stackoverflow.svg deleted file mode 100644 index d761498..0000000 --- a/svg/stackoverflow.svg +++ /dev/null @@ -1,6 +0,0 @@ - - - - - - \ No newline at end of file diff --git a/svg/twitch.svg b/svg/twitch.svg deleted file mode 100644 index 69ed9f0..0000000 --- a/svg/twitch.svg +++ /dev/null @@ -1,6 +0,0 @@ - -Twitch icon - - - - diff --git a/svg/twitter.svg b/svg/twitter.svg deleted file mode 100644 index ca7559b..0000000 --- a/svg/twitter.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/tailwind.config.js b/tailwind.config.js new file mode 100644 index 0000000..38278f7 --- /dev/null +++ b/tailwind.config.js @@ -0,0 +1,8 @@ +/** @type {import('tailwindcss').Config} */ +export default { + content: ['./index.html', './src/**/*.{js,jsx,ts,tsx}'], + theme: { + extend: {}, + }, + plugins: [], +}; diff --git a/vendor/CanvasRenderer.js b/vendor/CanvasRenderer.js deleted file mode 100644 index 0fb6a1c..0000000 --- a/vendor/CanvasRenderer.js +++ /dev/null @@ -1,1094 +0,0 @@ -/** - * @author mrdoob / http://mrdoob.com/ - */ - -THREE.SpriteCanvasMaterial = function ( parameters ) { - - THREE.Material.call( this ); - - this.type = 'SpriteCanvasMaterial'; - - this.color = new THREE.Color( 0xffffff ); - this.program = function ( context, color ) {}; - - this.setValues( parameters ); - -}; - -THREE.SpriteCanvasMaterial.prototype = Object.create( THREE.Material.prototype ); -THREE.SpriteCanvasMaterial.prototype.constructor = THREE.SpriteCanvasMaterial; - -THREE.SpriteCanvasMaterial.prototype.clone = function () { - - var material = new THREE.SpriteCanvasMaterial(); - - material.copy( this ); - material.color.copy( this.color ); - material.program = this.program; - - return material; - -}; - -// - -THREE.CanvasRenderer = function ( parameters ) { - - console.log( 'THREE.CanvasRenderer', THREE.REVISION ); - - parameters = parameters || {}; - - var _this = this, - _renderData, _elements, _lights, - _projector = new THREE.Projector(), - - _canvas = parameters.canvas !== undefined - ? parameters.canvas - : document.createElement( 'canvas' ), - - _canvasWidth = _canvas.width, - _canvasHeight = _canvas.height, - _canvasWidthHalf = Math.floor( _canvasWidth / 2 ), - _canvasHeightHalf = Math.floor( _canvasHeight / 2 ), - - _viewportX = 0, - _viewportY = 0, - _viewportWidth = _canvasWidth, - _viewportHeight = _canvasHeight, - - pixelRatio = 1, - - _context = _canvas.getContext( '2d', { - alpha: parameters.alpha === true - } ), - - _clearColor = new THREE.Color( 0x000000 ), - _clearAlpha = parameters.alpha === true ? 0 : 1, - - _contextGlobalAlpha = 1, - _contextGlobalCompositeOperation = 0, - _contextStrokeStyle = null, - _contextFillStyle = null, - _contextLineWidth = null, - _contextLineCap = null, - _contextLineJoin = null, - _contextLineDash = [], - - _camera, - - _v1, _v2, _v3, _v4, - _v5 = new THREE.RenderableVertex(), - _v6 = new THREE.RenderableVertex(), - - _v1x, _v1y, _v2x, _v2y, _v3x, _v3y, - _v4x, _v4y, _v5x, _v5y, _v6x, _v6y, - - _color = new THREE.Color(), - _color1 = new THREE.Color(), - _color2 = new THREE.Color(), - _color3 = new THREE.Color(), - _color4 = new THREE.Color(), - - _diffuseColor = new THREE.Color(), - _emissiveColor = new THREE.Color(), - - _lightColor = new THREE.Color(), - - _patterns = {}, - - _image, _uvs, - _uv1x, _uv1y, _uv2x, _uv2y, _uv3x, _uv3y, - - _clipBox = new THREE.Box2(), - _clearBox = new THREE.Box2(), - _elemBox = new THREE.Box2(), - - _ambientLight = new THREE.Color(), - _directionalLights = new THREE.Color(), - _pointLights = new THREE.Color(), - - _vector3 = new THREE.Vector3(), // Needed for PointLight - _centroid = new THREE.Vector3(), - _normal = new THREE.Vector3(), - _normalViewMatrix = new THREE.Matrix3(); - - // dash+gap fallbacks for Firefox and everything else - - if ( _context.setLineDash === undefined ) { - - _context.setLineDash = function () {} - - } - - this.domElement = _canvas; - - this.autoClear = true; - this.sortObjects = true; - this.sortElements = true; - - this.info = { - - render: { - - vertices: 0, - faces: 0 - - } - - }; - - // WebGLRenderer compatibility - - this.supportsVertexTextures = function () {}; - this.setFaceCulling = function () {}; - - // API - - this.getContext = function () { - - return _context; - - }; - - this.getContextAttributes = function () { - - return _context.getContextAttributes(); - - }; - - this.getPixelRatio = function () { - - return pixelRatio; - - }; - - this.setPixelRatio = function ( value ) { - - if ( value !== undefined ) pixelRatio = value; - - }; - - this.setSize = function ( width, height, updateStyle ) { - - _canvasWidth = width * pixelRatio; - _canvasHeight = height * pixelRatio; - - _canvas.width = _canvasWidth; - _canvas.height = _canvasHeight; - - _canvasWidthHalf = Math.floor( _canvasWidth / 2 ); - _canvasHeightHalf = Math.floor( _canvasHeight / 2 ); - - if ( updateStyle !== false ) { - - _canvas.style.width = width + 'px'; - _canvas.style.height = height + 'px'; - - } - - _clipBox.min.set( - _canvasWidthHalf, - _canvasHeightHalf ); - _clipBox.max.set( _canvasWidthHalf, _canvasHeightHalf ); - - _clearBox.min.set( - _canvasWidthHalf, - _canvasHeightHalf ); - _clearBox.max.set( _canvasWidthHalf, _canvasHeightHalf ); - - _contextGlobalAlpha = 1; - _contextGlobalCompositeOperation = 0; - _contextStrokeStyle = null; - _contextFillStyle = null; - _contextLineWidth = null; - _contextLineCap = null; - _contextLineJoin = null; - - this.setViewport( 0, 0, width, height ); - - }; - - this.setViewport = function ( x, y, width, height ) { - - _viewportX = x * pixelRatio; - _viewportY = y * pixelRatio; - - _viewportWidth = width * pixelRatio; - _viewportHeight = height * pixelRatio; - - }; - - this.setScissor = function () {}; - this.enableScissorTest = function () {}; - - this.setClearColor = function ( color, alpha ) { - - _clearColor.set( color ); - _clearAlpha = alpha !== undefined ? alpha : 1; - - _clearBox.min.set( - _canvasWidthHalf, - _canvasHeightHalf ); - _clearBox.max.set( _canvasWidthHalf, _canvasHeightHalf ); - - }; - - this.setClearColorHex = function ( hex, alpha ) { - - console.warn( 'THREE.CanvasRenderer: .setClearColorHex() is being removed. Use .setClearColor() instead.' ); - this.setClearColor( hex, alpha ); - - }; - - this.getClearColor = function () { - - return _clearColor; - - }; - - this.getClearAlpha = function () { - - return _clearAlpha; - - }; - - this.getMaxAnisotropy = function () { - - return 0; - - }; - - this.clear = function () { - - if ( _clearBox.empty() === false ) { - - _clearBox.intersect( _clipBox ); - _clearBox.expandByScalar( 2 ); - - _clearBox.min.x = _clearBox.min.x + _canvasWidthHalf; - _clearBox.min.y = - _clearBox.min.y + _canvasHeightHalf; // higher y value ! - _clearBox.max.x = _clearBox.max.x + _canvasWidthHalf; - _clearBox.max.y = - _clearBox.max.y + _canvasHeightHalf; // lower y value ! - - if ( _clearAlpha < 1 ) { - - _context.clearRect( - _clearBox.min.x | 0, - _clearBox.max.y | 0, - ( _clearBox.max.x - _clearBox.min.x ) | 0, - ( _clearBox.min.y - _clearBox.max.y ) | 0 - ); - - } - - if ( _clearAlpha > 0 ) { - - setBlending( THREE.NormalBlending ); - setOpacity( 1 ); - - setFillStyle( 'rgba(' + Math.floor( _clearColor.r * 255 ) + ',' + Math.floor( _clearColor.g * 255 ) + ',' + Math.floor( _clearColor.b * 255 ) + ',' + _clearAlpha + ')' ); - - _context.fillRect( - _clearBox.min.x | 0, - _clearBox.max.y | 0, - ( _clearBox.max.x - _clearBox.min.x ) | 0, - ( _clearBox.min.y - _clearBox.max.y ) | 0 - ); - - } - - _clearBox.makeEmpty(); - - } - - }; - - // compatibility - - this.clearColor = function () {}; - this.clearDepth = function () {}; - this.clearStencil = function () {}; - - this.render = function ( scene, camera ) { - - if ( camera instanceof THREE.Camera === false ) { - - console.error( 'THREE.CanvasRenderer.render: camera is not an instance of THREE.Camera.' ); - return; - - } - - if ( this.autoClear === true ) this.clear(); - - _this.info.render.vertices = 0; - _this.info.render.faces = 0; - - _context.setTransform( _viewportWidth / _canvasWidth, 0, 0, - _viewportHeight / _canvasHeight, _viewportX, _canvasHeight - _viewportY ); - _context.translate( _canvasWidthHalf, _canvasHeightHalf ); - - _renderData = _projector.projectScene( scene, camera, this.sortObjects, this.sortElements ); - _elements = _renderData.elements; - _lights = _renderData.lights; - _camera = camera; - - _normalViewMatrix.getNormalMatrix( camera.matrixWorldInverse ); - - /* DEBUG - setFillStyle( 'rgba( 0, 255, 255, 0.5 )' ); - _context.fillRect( _clipBox.min.x, _clipBox.min.y, _clipBox.max.x - _clipBox.min.x, _clipBox.max.y - _clipBox.min.y ); - */ - - calculateLights(); - - 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 *= _canvasWidthHalf; _v1.y *= _canvasHeightHalf; - - renderSprite( _v1, element, material ); - - } else if ( element instanceof THREE.RenderableLine ) { - - _v1 = element.v1; _v2 = element.v2; - - _v1.positionScreen.x *= _canvasWidthHalf; _v1.positionScreen.y *= _canvasHeightHalf; - _v2.positionScreen.x *= _canvasWidthHalf; _v2.positionScreen.y *= _canvasHeightHalf; - - _elemBox.setFromPoints( [ - _v1.positionScreen, - _v2.positionScreen - ] ); - - if ( _clipBox.isIntersectionBox( _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 *= _canvasWidthHalf; _v1.positionScreen.y *= _canvasHeightHalf; - _v2.positionScreen.x *= _canvasWidthHalf; _v2.positionScreen.y *= _canvasHeightHalf; - _v3.positionScreen.x *= _canvasWidthHalf; _v3.positionScreen.y *= _canvasHeightHalf; - - if ( material.overdraw > 0 ) { - - expand( _v1.positionScreen, _v2.positionScreen, material.overdraw ); - expand( _v2.positionScreen, _v3.positionScreen, material.overdraw ); - expand( _v3.positionScreen, _v1.positionScreen, material.overdraw ); - - } - - _elemBox.setFromPoints( [ - _v1.positionScreen, - _v2.positionScreen, - _v3.positionScreen - ] ); - - if ( _clipBox.isIntersectionBox( _elemBox ) === true ) { - - renderFace3( _v1, _v2, _v3, 0, 1, 2, element, material ); - - } - - } - - /* DEBUG - setLineWidth( 1 ); - setStrokeStyle( 'rgba( 0, 255, 0, 0.5 )' ); - _context.strokeRect( _elemBox.min.x, _elemBox.min.y, _elemBox.max.x - _elemBox.min.x, _elemBox.max.y - _elemBox.min.y ); - */ - - _clearBox.union( _elemBox ); - - } - - /* DEBUG - setLineWidth( 1 ); - setStrokeStyle( 'rgba( 255, 0, 0, 0.5 )' ); - _context.strokeRect( _clearBox.min.x, _clearBox.min.y, _clearBox.max.x - _clearBox.min.x, _clearBox.max.y - _clearBox.min.y ); - */ - - _context.setTransform( 1, 0, 0, 1, 0, 0 ); - - }; - - // - - function calculateLights() { - - _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.add( lightColor ); - - } else if ( light instanceof THREE.DirectionalLight ) { - - // for sprites - - _directionalLights.add( lightColor ); - - } else if ( light instanceof THREE.PointLight ) { - - // for sprites - - _pointLights.add( lightColor ); - - } - - } - - } - - function calculateLight( position, normal, color ) { - - for ( var l = 0, ll = _lights.length; l < ll; l ++ ) { - - var light = _lights[ l ]; - - _lightColor.copy( 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.add( _lightColor.multiplyScalar( 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.add( _lightColor.multiplyScalar( amount ) ); - - } - - } - - } - - function renderSprite( v1, element, material ) { - - setOpacity( material.opacity ); - setBlending( material.blending ); - - var scaleX = element.scale.x * _canvasWidthHalf; - var scaleY = element.scale.y * _canvasHeightHalf; - - var dist = 0.5 * Math.sqrt( scaleX * scaleX + scaleY * scaleY ); // allow for rotated sprite - _elemBox.min.set( v1.x - dist, v1.y - dist ); - _elemBox.max.set( v1.x + dist, v1.y + dist ); - - if ( material instanceof THREE.SpriteMaterial ) { - - var texture = material.map; - - if ( texture !== null ) { - - var pattern = _patterns[ texture.id ]; - - if ( pattern === undefined || pattern.version !== texture.version ) { - - pattern = textureToPattern( texture ); - _patterns[ texture.id ] = pattern; - - } - - if ( pattern.canvas !== undefined ) { - - setFillStyle( pattern.canvas ); - - var bitmap = texture.image; - - var ox = bitmap.width * texture.offset.x; - var oy = bitmap.height * texture.offset.y; - - var sx = bitmap.width * texture.repeat.x; - var sy = bitmap.height * texture.repeat.y; - - var cx = scaleX / sx; - var cy = scaleY / sy; - - _context.save(); - _context.translate( v1.x, v1.y ); - if ( material.rotation !== 0 ) _context.rotate( material.rotation ); - _context.translate( - scaleX / 2, - scaleY / 2 ); - _context.scale( cx, cy ); - _context.translate( - ox, - oy ); - _context.fillRect( ox, oy, sx, sy ); - _context.restore(); - - } - - } else { - - // no texture - - setFillStyle( material.color.getStyle() ); - - _context.save(); - _context.translate( v1.x, v1.y ); - if ( material.rotation !== 0 ) _context.rotate( material.rotation ); - _context.scale( scaleX, - scaleY ); - _context.fillRect( - 0.5, - 0.5, 1, 1 ); - _context.restore(); - - } - - } else if ( material instanceof THREE.SpriteCanvasMaterial ) { - - setStrokeStyle( material.color.getStyle() ); - setFillStyle( material.color.getStyle() ); - - _context.save(); - _context.translate( v1.x, v1.y ); - if ( material.rotation !== 0 ) _context.rotate( material.rotation ); - _context.scale( scaleX, scaleY ); - - material.program( _context ); - - _context.restore(); - - } - - /* DEBUG - setStrokeStyle( 'rgb(255,255,0)' ); - _context.beginPath(); - _context.moveTo( v1.x - 10, v1.y ); - _context.lineTo( v1.x + 10, v1.y ); - _context.moveTo( v1.x, v1.y - 10 ); - _context.lineTo( v1.x, v1.y + 10 ); - _context.stroke(); - */ - - } - - function renderLine( v1, v2, element, material ) { - - setOpacity( material.opacity ); - setBlending( material.blending ); - - _context.beginPath(); - _context.moveTo( v1.positionScreen.x, v1.positionScreen.y ); - _context.lineTo( v2.positionScreen.x, v2.positionScreen.y ); - - if ( material instanceof THREE.LineBasicMaterial ) { - - setLineWidth( material.linewidth ); - setLineCap( material.linecap ); - setLineJoin( material.linejoin ); - - if ( material.vertexColors !== THREE.VertexColors ) { - - setStrokeStyle( material.color.getStyle() ); - - } else { - - var colorStyle1 = element.vertexColors[ 0 ].getStyle(); - var colorStyle2 = element.vertexColors[ 1 ].getStyle(); - - if ( colorStyle1 === colorStyle2 ) { - - setStrokeStyle( colorStyle1 ); - - } else { - - try { - - var grad = _context.createLinearGradient( - v1.positionScreen.x, - v1.positionScreen.y, - v2.positionScreen.x, - v2.positionScreen.y - ); - grad.addColorStop( 0, colorStyle1 ); - grad.addColorStop( 1, colorStyle2 ); - - } catch ( exception ) { - - grad = colorStyle1; - - } - - setStrokeStyle( grad ); - - } - - } - - _context.stroke(); - _elemBox.expandByScalar( material.linewidth * 2 ); - - } else if ( material instanceof THREE.LineDashedMaterial ) { - - setLineWidth( material.linewidth ); - setLineCap( material.linecap ); - setLineJoin( material.linejoin ); - setStrokeStyle( material.color.getStyle() ); - setLineDash( [ material.dashSize, material.gapSize ] ); - - _context.stroke(); - - _elemBox.expandByScalar( material.linewidth * 2 ); - - setLineDash( [] ); - - } - - } - - function renderFace3( v1, v2, v3, uv1, uv2, uv3, element, material ) { - - _this.info.render.vertices += 3; - _this.info.render.faces ++; - - setOpacity( material.opacity ); - setBlending( material.blending ); - - _v1x = v1.positionScreen.x; _v1y = v1.positionScreen.y; - _v2x = v2.positionScreen.x; _v2y = v2.positionScreen.y; - _v3x = v3.positionScreen.x; _v3y = v3.positionScreen.y; - - drawTriangle( _v1x, _v1y, _v2x, _v2y, _v3x, _v3y ); - - if ( ( material instanceof THREE.MeshLambertMaterial || material instanceof THREE.MeshPhongMaterial ) && material.map === null ) { - - _diffuseColor.copy( material.color ); - _emissiveColor.copy( material.emissive ); - - 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( _centroid, element.normalModel, _color ); - - _color.multiply( _diffuseColor ).add( _emissiveColor ); - - material.wireframe === true - ? strokePath( _color, material.wireframeLinewidth, material.wireframeLinecap, material.wireframeLinejoin ) - : fillPath( _color ); - - } else if ( material instanceof THREE.MeshBasicMaterial || - material instanceof THREE.MeshLambertMaterial || - material instanceof THREE.MeshPhongMaterial ) { - - if ( material.map !== null ) { - - var mapping = material.map.mapping; - - if ( mapping === THREE.UVMapping ) { - - _uvs = element.uvs; - patternPath( _v1x, _v1y, _v2x, _v2y, _v3x, _v3y, _uvs[ uv1 ].x, _uvs[ uv1 ].y, _uvs[ uv2 ].x, _uvs[ uv2 ].y, _uvs[ uv3 ].x, _uvs[ uv3 ].y, material.map ); - - } - - } else if ( material.envMap !== null ) { - - if ( material.envMap.mapping === THREE.SphericalReflectionMapping ) { - - _normal.copy( element.vertexNormalsModel[ uv1 ] ).applyMatrix3( _normalViewMatrix ); - _uv1x = 0.5 * _normal.x + 0.5; - _uv1y = 0.5 * _normal.y + 0.5; - - _normal.copy( element.vertexNormalsModel[ uv2 ] ).applyMatrix3( _normalViewMatrix ); - _uv2x = 0.5 * _normal.x + 0.5; - _uv2y = 0.5 * _normal.y + 0.5; - - _normal.copy( element.vertexNormalsModel[ uv3 ] ).applyMatrix3( _normalViewMatrix ); - _uv3x = 0.5 * _normal.x + 0.5; - _uv3y = 0.5 * _normal.y + 0.5; - - patternPath( _v1x, _v1y, _v2x, _v2y, _v3x, _v3y, _uv1x, _uv1y, _uv2x, _uv2y, _uv3x, _uv3y, material.envMap ); - - } - - } else { - - _color.copy( material.color ); - - if ( material.vertexColors === THREE.FaceColors ) { - - _color.multiply( element.color ); - - } - - material.wireframe === true - ? strokePath( _color, material.wireframeLinewidth, material.wireframeLinecap, material.wireframeLinejoin ) - : fillPath( _color ); - - } - - } 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 ); - - material.wireframe === true - ? strokePath( _color, material.wireframeLinewidth, material.wireframeLinecap, material.wireframeLinejoin ) - : fillPath( _color ); - - } else { - - _color.setRGB( 1, 1, 1 ); - - material.wireframe === true - ? strokePath( _color, material.wireframeLinewidth, material.wireframeLinecap, material.wireframeLinejoin ) - : fillPath( _color ); - - } - - } - - // - - function drawTriangle( x0, y0, x1, y1, x2, y2 ) { - - _context.beginPath(); - _context.moveTo( x0, y0 ); - _context.lineTo( x1, y1 ); - _context.lineTo( x2, y2 ); - _context.closePath(); - - } - - function strokePath( color, linewidth, linecap, linejoin ) { - - setLineWidth( linewidth ); - setLineCap( linecap ); - setLineJoin( linejoin ); - setStrokeStyle( color.getStyle() ); - - _context.stroke(); - - _elemBox.expandByScalar( linewidth * 2 ); - - } - - function fillPath( color ) { - - setFillStyle( color.getStyle() ); - _context.fill(); - - } - - function textureToPattern( texture ) { - - if ( texture.version === 0 || - texture instanceof THREE.CompressedTexture || - texture instanceof THREE.DataTexture ) { - - return { - canvas: undefined, - version: texture.version - } - - } - - var image = texture.image; - - var canvas = document.createElement( 'canvas' ); - canvas.width = image.width; - canvas.height = image.height; - - var context = canvas.getContext( '2d' ); - context.setTransform( 1, 0, 0, - 1, 0, image.height ); - context.drawImage( image, 0, 0 ); - - var repeatX = texture.wrapS === THREE.RepeatWrapping; - var repeatY = texture.wrapT === THREE.RepeatWrapping; - - var repeat = 'no-repeat'; - - if ( repeatX === true && repeatY === true ) { - - repeat = 'repeat'; - - } else if ( repeatX === true ) { - - repeat = 'repeat-x'; - - } else if ( repeatY === true ) { - - repeat = 'repeat-y'; - - } - - return { - canvas: _context.createPattern( canvas, repeat ), - version: texture.version - } - - } - - function patternPath( x0, y0, x1, y1, x2, y2, u0, v0, u1, v1, u2, v2, texture ) { - - var pattern = _patterns[ texture.id ]; - - if ( pattern === undefined || pattern.version !== texture.version ) { - - pattern = textureToPattern( texture ); - _patterns[ texture.id ] = pattern; - - } - - if ( pattern.canvas !== undefined ) { - - setFillStyle( pattern.canvas ); - - } else { - - setFillStyle( 'rgba( 0, 0, 0, 1)' ); - _context.fill(); - return; - - } - - // http://extremelysatisfactorytotalitarianism.com/blog/?p=2120 - - var a, b, c, d, e, f, det, idet, - offsetX = texture.offset.x / texture.repeat.x, - offsetY = texture.offset.y / texture.repeat.y, - width = texture.image.width * texture.repeat.x, - height = texture.image.height * texture.repeat.y; - - u0 = ( u0 + offsetX ) * width; - v0 = ( v0 + offsetY ) * height; - - u1 = ( u1 + offsetX ) * width; - v1 = ( v1 + offsetY ) * height; - - u2 = ( u2 + offsetX ) * width; - v2 = ( v2 + offsetY ) * height; - - x1 -= x0; y1 -= y0; - x2 -= x0; y2 -= y0; - - u1 -= u0; v1 -= v0; - u2 -= u0; v2 -= v0; - - det = u1 * v2 - u2 * v1; - - if ( det === 0 ) return; - - idet = 1 / det; - - a = ( v2 * x1 - v1 * x2 ) * idet; - b = ( v2 * y1 - v1 * y2 ) * idet; - c = ( u1 * x2 - u2 * x1 ) * idet; - d = ( u1 * y2 - u2 * y1 ) * idet; - - e = x0 - a * u0 - c * v0; - f = y0 - b * u0 - d * v0; - - _context.save(); - _context.transform( a, b, c, d, e, f ); - _context.fill(); - _context.restore(); - - } - - function clipImage( x0, y0, x1, y1, x2, y2, u0, v0, u1, v1, u2, v2, image ) { - - // http://extremelysatisfactorytotalitarianism.com/blog/?p=2120 - - var a, b, c, d, e, f, det, idet, - width = image.width - 1, - height = image.height - 1; - - u0 *= width; v0 *= height; - u1 *= width; v1 *= height; - u2 *= width; v2 *= height; - - x1 -= x0; y1 -= y0; - x2 -= x0; y2 -= y0; - - u1 -= u0; v1 -= v0; - u2 -= u0; v2 -= v0; - - det = u1 * v2 - u2 * v1; - - idet = 1 / det; - - a = ( v2 * x1 - v1 * x2 ) * idet; - b = ( v2 * y1 - v1 * y2 ) * idet; - c = ( u1 * x2 - u2 * x1 ) * idet; - d = ( u1 * y2 - u2 * y1 ) * idet; - - e = x0 - a * u0 - c * v0; - f = y0 - b * u0 - d * v0; - - _context.save(); - _context.transform( a, b, c, d, e, f ); - _context.clip(); - _context.drawImage( image, 0, 0 ); - _context.restore(); - - } - - // Hide anti-alias gaps - - function expand( v1, v2, pixels ) { - - var x = v2.x - v1.x, y = v2.y - v1.y, - det = x * x + y * y, idet; - - if ( det === 0 ) return; - - idet = pixels / Math.sqrt( det ); - - x *= idet; y *= idet; - - v2.x += x; v2.y += y; - v1.x -= x; v1.y -= y; - - } - - // Context cached methods. - - function setOpacity( value ) { - - if ( _contextGlobalAlpha !== value ) { - - _context.globalAlpha = value; - _contextGlobalAlpha = value; - - } - - } - - function setBlending( value ) { - - if ( _contextGlobalCompositeOperation !== value ) { - - if ( value === THREE.NormalBlending ) { - - _context.globalCompositeOperation = 'source-over'; - - } else if ( value === THREE.AdditiveBlending ) { - - _context.globalCompositeOperation = 'lighter'; - - } else if ( value === THREE.SubtractiveBlending ) { - - _context.globalCompositeOperation = 'darker'; - - } - - _contextGlobalCompositeOperation = value; - - } - - } - - function setLineWidth( value ) { - - if ( _contextLineWidth !== value ) { - - _context.lineWidth = value; - _contextLineWidth = value; - - } - - } - - function setLineCap( value ) { - - // "butt", "round", "square" - - if ( _contextLineCap !== value ) { - - _context.lineCap = value; - _contextLineCap = value; - - } - - } - - function setLineJoin( value ) { - - // "round", "bevel", "miter" - - if ( _contextLineJoin !== value ) { - - _context.lineJoin = value; - _contextLineJoin = value; - - } - - } - - function setStrokeStyle( value ) { - - if ( _contextStrokeStyle !== value ) { - - _context.strokeStyle = value; - _contextStrokeStyle = value; - - } - - } - - function setFillStyle( value ) { - - if ( _contextFillStyle !== value ) { - - _context.fillStyle = value; - _contextFillStyle = value; - - } - - } - - function setLineDash( value ) { - - if ( _contextLineDash.length !== value.length ) { - - _context.setLineDash( value ); - _contextLineDash = value; - - } - - } - -}; diff --git a/vendor/Projector.js b/vendor/Projector.js deleted file mode 100644 index ac55d7a..0000000 --- a/vendor/Projector.js +++ /dev/null @@ -1,921 +0,0 @@ -/** - * @author mrdoob / http://mrdoob.com/ - * @author supereggbert / http://www.paulbrunt.co.uk/ - * @author julianwa / https://github.com/julianwa - */ - -THREE.RenderableObject = function () { - - this.id = 0; - - this.object = null; - this.z = 0; - this.renderOrder = 0; - -}; - -// - -THREE.RenderableFace = function () { - - this.id = 0; - - this.v1 = new THREE.RenderableVertex(); - this.v2 = new THREE.RenderableVertex(); - this.v3 = new THREE.RenderableVertex(); - - this.normalModel = new THREE.Vector3(); - - this.vertexNormalsModel = [ new THREE.Vector3(), new THREE.Vector3(), new THREE.Vector3() ]; - this.vertexNormalsLength = 0; - - this.color = new THREE.Color(); - this.material = null; - this.uvs = [ new THREE.Vector2(), new THREE.Vector2(), new THREE.Vector2() ]; - - this.z = 0; - this.renderOrder = 0; - -}; - -// - -THREE.RenderableVertex = function () { - - this.position = new THREE.Vector3(); - this.positionWorld = new THREE.Vector3(); - this.positionScreen = new THREE.Vector4(); - - this.visible = true; - -}; - -THREE.RenderableVertex.prototype.copy = function ( vertex ) { - - this.positionWorld.copy( vertex.positionWorld ); - this.positionScreen.copy( vertex.positionScreen ); - -}; - -// - -THREE.RenderableLine = function () { - - this.id = 0; - - this.v1 = new THREE.RenderableVertex(); - this.v2 = new THREE.RenderableVertex(); - - this.vertexColors = [ new THREE.Color(), new THREE.Color() ]; - this.material = null; - - this.z = 0; - this.renderOrder = 0; - -}; - -// - -THREE.RenderableSprite = function () { - - this.id = 0; - - this.object = null; - - this.x = 0; - this.y = 0; - this.z = 0; - - this.rotation = 0; - this.scale = new THREE.Vector2(); - - this.material = null; - this.renderOrder = 0; - -}; - -// - -THREE.Projector = function () { - - var _object, _objectCount, _objectPool = [], _objectPoolLength = 0, - _vertex, _vertexCount, _vertexPool = [], _vertexPoolLength = 0, - _face, _faceCount, _facePool = [], _facePoolLength = 0, - _line, _lineCount, _linePool = [], _linePoolLength = 0, - _sprite, _spriteCount, _spritePool = [], _spritePoolLength = 0, - - _renderData = { objects: [], lights: [], elements: [] }, - - _vector3 = new THREE.Vector3(), - _vector4 = new THREE.Vector4(), - - _clipBox = new THREE.Box3( new THREE.Vector3( - 1, - 1, - 1 ), new THREE.Vector3( 1, 1, 1 ) ), - _boundingBox = new THREE.Box3(), - _points3 = new Array( 3 ), - _points4 = new Array( 4 ), - - _viewMatrix = new THREE.Matrix4(), - _viewProjectionMatrix = new THREE.Matrix4(), - - _modelMatrix, - _modelViewProjectionMatrix = new THREE.Matrix4(), - - _normalMatrix = new THREE.Matrix3(), - - _frustum = new THREE.Frustum(), - - _clippedVertex1PositionScreen = new THREE.Vector4(), - _clippedVertex2PositionScreen = new THREE.Vector4(); - - // - - this.projectVector = function ( vector, camera ) { - - console.warn( 'THREE.Projector: .projectVector() is now vector.project().' ); - vector.project( camera ); - - }; - - this.unprojectVector = function ( vector, camera ) { - - console.warn( 'THREE.Projector: .unprojectVector() is now vector.unproject().' ); - vector.unproject( camera ); - - }; - - this.pickingRay = function ( vector, camera ) { - - console.error( 'THREE.Projector: .pickingRay() is now raycaster.setFromCamera().' ); - - }; - - // - - var RenderList = function () { - - var normals = []; - var uvs = []; - - var object = null; - var material = null; - - var normalMatrix = new THREE.Matrix3(); - - var setObject = function ( value ) { - - object = value; - material = object.material; - - normalMatrix.getNormalMatrix( object.matrixWorld ); - - normals.length = 0; - uvs.length = 0; - - }; - - var projectVertex = function ( vertex ) { - - var position = vertex.position; - var positionWorld = vertex.positionWorld; - var positionScreen = vertex.positionScreen; - - positionWorld.copy( position ).applyMatrix4( _modelMatrix ); - positionScreen.copy( positionWorld ).applyMatrix4( _viewProjectionMatrix ); - - var invW = 1 / positionScreen.w; - - positionScreen.x *= invW; - positionScreen.y *= invW; - positionScreen.z *= invW; - - vertex.visible = positionScreen.x >= - 1 && positionScreen.x <= 1 && - positionScreen.y >= - 1 && positionScreen.y <= 1 && - positionScreen.z >= - 1 && positionScreen.z <= 1; - - }; - - var pushVertex = function ( x, y, z ) { - - _vertex = getNextVertexInPool(); - _vertex.position.set( x, y, z ); - - projectVertex( _vertex ); - - }; - - var pushNormal = function ( x, y, z ) { - - normals.push( x, y, z ); - - }; - - var pushUv = function ( x, y ) { - - uvs.push( x, y ); - - }; - - var checkTriangleVisibility = function ( v1, v2, v3 ) { - - if ( v1.visible === true || v2.visible === true || v3.visible === true ) return true; - - _points3[ 0 ] = v1.positionScreen; - _points3[ 1 ] = v2.positionScreen; - _points3[ 2 ] = v3.positionScreen; - - return _clipBox.isIntersectionBox( _boundingBox.setFromPoints( _points3 ) ); - - }; - - var checkBackfaceCulling = function ( v1, v2, v3 ) { - - return ( ( v3.positionScreen.x - v1.positionScreen.x ) * - ( v2.positionScreen.y - v1.positionScreen.y ) - - ( v3.positionScreen.y - v1.positionScreen.y ) * - ( v2.positionScreen.x - v1.positionScreen.x ) ) < 0; - - }; - - var pushLine = function ( a, b ) { - - var v1 = _vertexPool[ a ]; - var v2 = _vertexPool[ b ]; - - _line = getNextLineInPool(); - - _line.id = object.id; - _line.v1.copy( v1 ); - _line.v2.copy( v2 ); - _line.z = ( v1.positionScreen.z + v2.positionScreen.z ) / 2; - _line.renderOrder = object.renderOrder; - - _line.material = object.material; - - _renderData.elements.push( _line ); - - }; - - var pushTriangle = function ( a, b, c ) { - - var v1 = _vertexPool[ a ]; - var v2 = _vertexPool[ b ]; - var v3 = _vertexPool[ c ]; - - if ( checkTriangleVisibility( v1, v2, v3 ) === false ) return; - - if ( material.side === THREE.DoubleSide || checkBackfaceCulling( v1, v2, v3 ) === true ) { - - _face = getNextFaceInPool(); - - _face.id = object.id; - _face.v1.copy( v1 ); - _face.v2.copy( v2 ); - _face.v3.copy( v3 ); - _face.z = ( v1.positionScreen.z + v2.positionScreen.z + v3.positionScreen.z ) / 3; - _face.renderOrder = object.renderOrder; - - // use first vertex normal as face normal - - _face.normalModel.fromArray( normals, a * 3 ); - _face.normalModel.applyMatrix3( normalMatrix ).normalize(); - - for ( var i = 0; i < 3; i ++ ) { - - var normal = _face.vertexNormalsModel[ i ]; - normal.fromArray( normals, arguments[ i ] * 3 ); - normal.applyMatrix3( normalMatrix ).normalize(); - - var uv = _face.uvs[ i ]; - uv.fromArray( uvs, arguments[ i ] * 2 ); - - } - - _face.vertexNormalsLength = 3; - - _face.material = object.material; - - _renderData.elements.push( _face ); - - } - - }; - - return { - setObject: setObject, - projectVertex: projectVertex, - checkTriangleVisibility: checkTriangleVisibility, - checkBackfaceCulling: checkBackfaceCulling, - pushVertex: pushVertex, - pushNormal: pushNormal, - pushUv: pushUv, - pushLine: pushLine, - pushTriangle: pushTriangle - } - - }; - - var renderList = new RenderList(); - - this.projectScene = function ( scene, camera, sortObjects, sortElements ) { - - _faceCount = 0; - _lineCount = 0; - _spriteCount = 0; - - _renderData.elements.length = 0; - - if ( scene.autoUpdate === true ) scene.updateMatrixWorld(); - if ( camera.parent === null ) camera.updateMatrixWorld(); - - _viewMatrix.copy( camera.matrixWorldInverse.getInverse( camera.matrixWorld ) ); - _viewProjectionMatrix.multiplyMatrices( camera.projectionMatrix, _viewMatrix ); - - _frustum.setFromMatrix( _viewProjectionMatrix ); - - // - - _objectCount = 0; - - _renderData.objects.length = 0; - _renderData.lights.length = 0; - - scene.traverseVisible( function ( object ) { - - if ( object instanceof THREE.Light ) { - - _renderData.lights.push( object ); - - } else if ( object instanceof THREE.Mesh || object instanceof THREE.Line || object instanceof THREE.Sprite ) { - - var material = object.material; - - if ( material.visible === false ) return; - - if ( object.frustumCulled === false || _frustum.intersectsObject( object ) === true ) { - - _object = getNextObjectInPool(); - _object.id = object.id; - _object.object = object; - - _vector3.setFromMatrixPosition( object.matrixWorld ); - _vector3.applyProjection( _viewProjectionMatrix ); - _object.z = _vector3.z; - _object.renderOrder = object.renderOrder; - - _renderData.objects.push( _object ); - - } - - } - - } ); - - if ( sortObjects === true ) { - - _renderData.objects.sort( painterSort ); - - } - - // - - for ( var o = 0, ol = _renderData.objects.length; o < ol; o ++ ) { - - var object = _renderData.objects[ o ].object; - var geometry = object.geometry; - - renderList.setObject( object ); - - _modelMatrix = object.matrixWorld; - - _vertexCount = 0; - - if ( object instanceof THREE.Mesh ) { - - if ( geometry instanceof THREE.BufferGeometry ) { - - var attributes = geometry.attributes; - var groups = geometry.groups; - - if ( attributes.position === undefined ) continue; - - var positions = attributes.position.array; - - for ( var i = 0, l = positions.length; i < l; i += 3 ) { - - renderList.pushVertex( positions[ i ], positions[ i + 1 ], positions[ i + 2 ] ); - - } - - if ( attributes.normal !== undefined ) { - - var normals = attributes.normal.array; - - for ( var i = 0, l = normals.length; i < l; i += 3 ) { - - renderList.pushNormal( normals[ i ], normals[ i + 1 ], normals[ i + 2 ] ); - - } - - } - - if ( attributes.uv !== undefined ) { - - var uvs = attributes.uv.array; - - for ( var i = 0, l = uvs.length; i < l; i += 2 ) { - - renderList.pushUv( uvs[ i ], uvs[ i + 1 ] ); - - } - - } - - if ( geometry.index !== null ) { - - var indices = geometry.index.array; - - if ( groups.length > 0 ) { - - for ( var o = 0; o < groups.length; o ++ ) { - - var group = groups[ o ]; - - for ( var i = group.start, l = group.start + group.count; i < l; i += 3 ) { - - renderList.pushTriangle( indices[ i ], indices[ i + 1 ], indices[ i + 2 ] ); - - } - - } - - } else { - - for ( var i = 0, l = indices.length; i < l; i += 3 ) { - - renderList.pushTriangle( indices[ i ], indices[ i + 1 ], indices[ i + 2 ] ); - - } - - } - - } else { - - for ( var i = 0, l = positions.length / 3; i < l; i += 3 ) { - - renderList.pushTriangle( i, i + 1, i + 2 ); - - } - - } - - } else if ( geometry instanceof THREE.Geometry ) { - - var vertices = geometry.vertices; - var faces = geometry.faces; - var faceVertexUvs = geometry.faceVertexUvs[ 0 ]; - - _normalMatrix.getNormalMatrix( _modelMatrix ); - - var material = object.material; - - var isFaceMaterial = material instanceof THREE.MeshFaceMaterial; - var objectMaterials = isFaceMaterial === true ? object.material : null; - - for ( var v = 0, vl = vertices.length; v < vl; v ++ ) { - - var vertex = vertices[ v ]; - - _vector3.copy( vertex ); - - if ( material.morphTargets === true ) { - - var morphTargets = geometry.morphTargets; - var morphInfluences = object.morphTargetInfluences; - - for ( var t = 0, tl = morphTargets.length; t < tl; t ++ ) { - - var influence = morphInfluences[ t ]; - - if ( influence === 0 ) continue; - - var target = morphTargets[ t ]; - var targetVertex = target.vertices[ v ]; - - _vector3.x += ( targetVertex.x - vertex.x ) * influence; - _vector3.y += ( targetVertex.y - vertex.y ) * influence; - _vector3.z += ( targetVertex.z - vertex.z ) * influence; - - } - - } - - renderList.pushVertex( _vector3.x, _vector3.y, _vector3.z ); - - } - - for ( var f = 0, fl = faces.length; f < fl; f ++ ) { - - var face = faces[ f ]; - - material = isFaceMaterial === true - ? objectMaterials.materials[ face.materialIndex ] - : object.material; - - if ( material === undefined ) continue; - - var side = material.side; - - var v1 = _vertexPool[ face.a ]; - var v2 = _vertexPool[ face.b ]; - var v3 = _vertexPool[ face.c ]; - - if ( renderList.checkTriangleVisibility( v1, v2, v3 ) === false ) continue; - - var visible = renderList.checkBackfaceCulling( v1, v2, v3 ); - - if ( side !== THREE.DoubleSide ) { - - if ( side === THREE.FrontSide && visible === false ) continue; - if ( side === THREE.BackSide && visible === true ) continue; - - } - - _face = getNextFaceInPool(); - - _face.id = object.id; - _face.v1.copy( v1 ); - _face.v2.copy( v2 ); - _face.v3.copy( v3 ); - - _face.normalModel.copy( face.normal ); - - if ( visible === false && ( side === THREE.BackSide || side === THREE.DoubleSide ) ) { - - _face.normalModel.negate(); - - } - - _face.normalModel.applyMatrix3( _normalMatrix ).normalize(); - - var faceVertexNormals = face.vertexNormals; - - for ( var n = 0, nl = Math.min( faceVertexNormals.length, 3 ); n < nl; n ++ ) { - - var normalModel = _face.vertexNormalsModel[ n ]; - normalModel.copy( faceVertexNormals[ n ] ); - - if ( visible === false && ( side === THREE.BackSide || side === THREE.DoubleSide ) ) { - - normalModel.negate(); - - } - - normalModel.applyMatrix3( _normalMatrix ).normalize(); - - } - - _face.vertexNormalsLength = faceVertexNormals.length; - - var vertexUvs = faceVertexUvs[ f ]; - - if ( vertexUvs !== undefined ) { - - for ( var u = 0; u < 3; u ++ ) { - - _face.uvs[ u ].copy( vertexUvs[ u ] ); - - } - - } - - _face.color = face.color; - _face.material = material; - - _face.z = ( v1.positionScreen.z + v2.positionScreen.z + v3.positionScreen.z ) / 3; - _face.renderOrder = object.renderOrder; - - _renderData.elements.push( _face ); - - } - - } - - } else if ( object instanceof THREE.Line ) { - - if ( geometry instanceof THREE.BufferGeometry ) { - - var attributes = geometry.attributes; - - if ( attributes.position !== undefined ) { - - var positions = attributes.position.array; - - for ( var i = 0, l = positions.length; i < l; i += 3 ) { - - renderList.pushVertex( positions[ i ], positions[ i + 1 ], positions[ i + 2 ] ); - - } - - if ( geometry.index !== null ) { - - var indices = geometry.index.array; - - for ( var i = 0, l = indices.length; i < l; i += 2 ) { - - renderList.pushLine( indices[ i ], indices[ i + 1 ] ); - - } - - } else { - - var step = object instanceof THREE.LineSegments ? 2 : 1; - - for ( var i = 0, l = ( positions.length / 3 ) - 1; i < l; i += step ) { - - renderList.pushLine( i, i + 1 ); - - } - - } - - } - - } else if ( geometry instanceof THREE.Geometry ) { - - _modelViewProjectionMatrix.multiplyMatrices( _viewProjectionMatrix, _modelMatrix ); - - var vertices = object.geometry.vertices; - - if ( vertices.length === 0 ) continue; - - v1 = getNextVertexInPool(); - v1.positionScreen.copy( vertices[ 0 ] ).applyMatrix4( _modelViewProjectionMatrix ); - - var step = object instanceof THREE.LineSegments ? 2 : 1; - - for ( var v = 1, vl = vertices.length; v < vl; v ++ ) { - - v1 = getNextVertexInPool(); - v1.positionScreen.copy( vertices[ v ] ).applyMatrix4( _modelViewProjectionMatrix ); - - if ( ( v + 1 ) % step > 0 ) continue; - - v2 = _vertexPool[ _vertexCount - 2 ]; - - _clippedVertex1PositionScreen.copy( v1.positionScreen ); - _clippedVertex2PositionScreen.copy( v2.positionScreen ); - - if ( clipLine( _clippedVertex1PositionScreen, _clippedVertex2PositionScreen ) === true ) { - - // Perform the perspective divide - _clippedVertex1PositionScreen.multiplyScalar( 1 / _clippedVertex1PositionScreen.w ); - _clippedVertex2PositionScreen.multiplyScalar( 1 / _clippedVertex2PositionScreen.w ); - - _line = getNextLineInPool(); - - _line.id = object.id; - _line.v1.positionScreen.copy( _clippedVertex1PositionScreen ); - _line.v2.positionScreen.copy( _clippedVertex2PositionScreen ); - - _line.z = Math.max( _clippedVertex1PositionScreen.z, _clippedVertex2PositionScreen.z ); - _line.renderOrder = object.renderOrder; - - _line.material = object.material; - - if ( object.material.vertexColors === THREE.VertexColors ) { - - _line.vertexColors[ 0 ].copy( object.geometry.colors[ v ] ); - _line.vertexColors[ 1 ].copy( object.geometry.colors[ v - 1 ] ); - - } - - _renderData.elements.push( _line ); - - } - - } - - } - - } else if ( object instanceof THREE.Sprite ) { - - _vector4.set( _modelMatrix.elements[ 12 ], _modelMatrix.elements[ 13 ], _modelMatrix.elements[ 14 ], 1 ); - _vector4.applyMatrix4( _viewProjectionMatrix ); - - var invW = 1 / _vector4.w; - - _vector4.z *= invW; - - if ( _vector4.z >= - 1 && _vector4.z <= 1 ) { - - _sprite = getNextSpriteInPool(); - _sprite.id = object.id; - _sprite.x = _vector4.x * invW; - _sprite.y = _vector4.y * invW; - _sprite.z = _vector4.z; - _sprite.renderOrder = object.renderOrder; - _sprite.object = object; - - _sprite.rotation = object.rotation; - - _sprite.scale.x = object.scale.x * Math.abs( _sprite.x - ( _vector4.x + camera.projectionMatrix.elements[ 0 ] ) / ( _vector4.w + camera.projectionMatrix.elements[ 12 ] ) ); - _sprite.scale.y = object.scale.y * Math.abs( _sprite.y - ( _vector4.y + camera.projectionMatrix.elements[ 5 ] ) / ( _vector4.w + camera.projectionMatrix.elements[ 13 ] ) ); - - _sprite.material = object.material; - - _renderData.elements.push( _sprite ); - - } - - } - - } - - if ( sortElements === true ) { - - _renderData.elements.sort( painterSort ); - - } - - return _renderData; - - }; - - // Pools - - function getNextObjectInPool() { - - if ( _objectCount === _objectPoolLength ) { - - var object = new THREE.RenderableObject(); - _objectPool.push( object ); - _objectPoolLength ++; - _objectCount ++; - return object; - - } - - return _objectPool[ _objectCount ++ ]; - - } - - function getNextVertexInPool() { - - if ( _vertexCount === _vertexPoolLength ) { - - var vertex = new THREE.RenderableVertex(); - _vertexPool.push( vertex ); - _vertexPoolLength ++; - _vertexCount ++; - return vertex; - - } - - return _vertexPool[ _vertexCount ++ ]; - - } - - function getNextFaceInPool() { - - if ( _faceCount === _facePoolLength ) { - - var face = new THREE.RenderableFace(); - _facePool.push( face ); - _facePoolLength ++; - _faceCount ++; - return face; - - } - - return _facePool[ _faceCount ++ ]; - - - } - - function getNextLineInPool() { - - if ( _lineCount === _linePoolLength ) { - - var line = new THREE.RenderableLine(); - _linePool.push( line ); - _linePoolLength ++; - _lineCount ++; - return line; - - } - - return _linePool[ _lineCount ++ ]; - - } - - function getNextSpriteInPool() { - - if ( _spriteCount === _spritePoolLength ) { - - var sprite = new THREE.RenderableSprite(); - _spritePool.push( sprite ); - _spritePoolLength ++; - _spriteCount ++; - return sprite; - - } - - return _spritePool[ _spriteCount ++ ]; - - } - - // - - function painterSort( a, b ) { - - if ( a.renderOrder !== b.renderOrder ) { - - return a.renderOrder - b.renderOrder; - - } else if ( a.z !== b.z ) { - - return b.z - a.z; - - } else if ( a.id !== b.id ) { - - return a.id - b.id; - - } else { - - return 0; - - } - - } - - function clipLine( s1, s2 ) { - - var alpha1 = 0, alpha2 = 1, - - // Calculate the boundary coordinate of each vertex for the near and far clip planes, - // Z = -1 and Z = +1, respectively. - bc1near = s1.z + s1.w, - bc2near = s2.z + s2.w, - bc1far = - s1.z + s1.w, - bc2far = - s2.z + s2.w; - - if ( bc1near >= 0 && bc2near >= 0 && bc1far >= 0 && bc2far >= 0 ) { - - // Both vertices lie entirely within all clip planes. - return true; - - } else if ( ( bc1near < 0 && bc2near < 0 ) || ( bc1far < 0 && bc2far < 0 ) ) { - - // Both vertices lie entirely outside one of the clip planes. - return false; - - } else { - - // The line segment spans at least one clip plane. - - if ( bc1near < 0 ) { - - // v1 lies outside the near plane, v2 inside - alpha1 = Math.max( alpha1, bc1near / ( bc1near - bc2near ) ); - - } else if ( bc2near < 0 ) { - - // v2 lies outside the near plane, v1 inside - alpha2 = Math.min( alpha2, bc1near / ( bc1near - bc2near ) ); - - } - - if ( bc1far < 0 ) { - - // v1 lies outside the far plane, v2 inside - alpha1 = Math.max( alpha1, bc1far / ( bc1far - bc2far ) ); - - } else if ( bc2far < 0 ) { - - // v2 lies outside the far plane, v2 inside - alpha2 = Math.min( alpha2, bc1far / ( bc1far - bc2far ) ); - - } - - if ( alpha2 < alpha1 ) { - - // The line segment spans two boundaries, but is outside both of them. - // (This can't happen when we're only clipping against just near/far but good - // to leave the check here for future usage if other clip planes are added.) - return false; - - } else { - - // Update the s1 and s2 vertices to match the clipped line segment. - s1.lerp( s2, alpha1 ); - s2.lerp( s1, 1 - alpha2 ); - - return true; - - } - - } - - } - -}; diff --git a/vendor/stats.min.js b/vendor/stats.min.js deleted file mode 100644 index a2d1872..0000000 --- a/vendor/stats.min.js +++ /dev/null @@ -1,5 +0,0 @@ -// stats.js - http://github.com/mrdoob/stats.js -var Stats=function(){function f(a,e,b){a=document.createElement(a);a.id=e;a.style.cssText=b;return a}function l(a,e,b){var c=f("div",a,"padding:0 0 3px 3px;text-align:left;background:"+b),d=f("div",a+"Text","font-family:Helvetica,Arial,sans-serif;font-size:9px;font-weight:bold;line-height:15px;color:"+e);d.innerHTML=a.toUpperCase();c.appendChild(d);a=f("div",a+"Graph","width:74px;height:30px;background:"+e);c.appendChild(a);for(e=0;74>e;e++)a.appendChild(f("span","","width:1px;height:30px;float:left;opacity:0.9;background:"+ -b));return c}function m(a){for(var b=c.children,d=0;dr+1E3&&(d=Math.round(1E3* -t/(a-r)),u=Math.min(u,d),v=Math.max(v,d),A.textContent=d+" FPS ("+u+"-"+v+")",p(B,d/100),r=a,t=0,void 0!==h)){var b=performance.memory.usedJSHeapSize,c=performance.memory.jsHeapSizeLimit;h=Math.round(9.54E-7*b);y=Math.min(y,h);z=Math.max(z,h);E.textContent=h+" MB ("+y+"-"+z+")";p(F,b/c)}return a},update:function(){k=this.end()}}};"object"===typeof module&&(module.exports=Stats); diff --git a/vite.config.js b/vite.config.js new file mode 100644 index 0000000..c049f46 --- /dev/null +++ b/vite.config.js @@ -0,0 +1,3 @@ +import { defineConfig } from 'vite'; + +export default defineConfig({});