diff --git a/Gruntfile.coffee b/Gruntfile.coffee index dba9fd47e..1365fec7c 100644 --- a/Gruntfile.coffee +++ b/Gruntfile.coffee @@ -1,45 +1,36 @@ -### -# Crafting Guide - Gruntfile.coffee # -# Copyright (c) 2014 by Redwood Labs +# Copyright © 2015 by Redwood Labs # All rights reserved. -### +# -fs = require 'fs' -util = require 'util' - -######################################################################################################################## - -LIBRARY_ALIAS_MAPPING = [ - './node_modules/backbone/backbone.js:backbone' - './node_modules/jade/runtime.js:jade' - './node_modules/jquery/dist/jquery.js:jquery' - './node_modules/underscore/underscore.js:underscore' - './node_modules/when/when.js:when' +EXTERNAL_LIBS = [ + 'backbone' + 'jquery' + 'marked' + 'underscore' + 'underscore.inflections' + 'when' + './vendor/email.js:emailjs' ] -LIBRARIES = (s.substring(0, s.indexOf(':')) for s in LIBRARY_ALIAS_MAPPING) -ALIASES = (s.substring(s.indexOf(':') + 1) for s in LIBRARY_ALIAS_MAPPING) +######################################################################################################################## module.exports = (grunt)-> grunt.loadTasks tasks for tasks in grunt.file.expand './node_modules/grunt-*/tasks' grunt.config.init - browserify: - dev: + + compress: + static: options: - browserifyOptions: - debug: true - extensions: ['.coffee'] - transform: ['coffeeify'] - files: './dist/js/main.js': ['./src/coffee/main.coffee'] - prod: - options: - browserifyOptions: - extensions: ['.coffee'] - transform: ['coffeeify'] - files: './dist/js/main.js': ['./src/coffee/main.coffee'] + mode: 'gzip' + files: [ + {expand: true, cwd:'./build/static', src:'**/*.css', dest:'./dist/'} + {expand: true, cwd:'./build/static', src:'**/*.html', dest:'./dist/'} + {expand: true, cwd:'./build/static', src:'**/*.js', dest:'./dist/'} + {expand: true, cwd:'./build/static', src:'**/*.json', dest:'./dist/'} + ] coffee: dev: @@ -47,16 +38,30 @@ module.exports = (grunt)-> sourceMap: true files: [expand:true, cwd:'./src/coffee', src:'**/*.coffee', dest:'./dist', ext:'.js'] - clean: - dist: ['./dist'] - copy: - styles: - files: [expand:true, cwd:'./src/css', src:'**/*.scss', dest:'./dist/src/css'] + server_source: + files: [ + {expand:true, cwd:'./src/server', src:'**/*.coffee', dest:'./build/', ext:'.coffee'} + ] + common_source: + files: [ + {expand:true, cwd:'./src/common', src:'**/*.coffee', dest:'./build/', ext:'.coffee'} + ] + assets_build: + files: [ + {expand:true, cwd:'./assets/', src:'**/*', dest:'./build/static/'} + ] + assets_dist: + files: [ + {expand:true, cwd:'./assets/', src:'**/*.mp3', dest:'./dist/'} + {expand:true, cwd:'./assets/', src:'**/*.png', dest:'./dist/'} + ] - exorcise: - dev: - files: './dist/js/main.js.map': ['./dist/js/main.js'] + clean: + assets: ['./build/static/data', './build/static/images'] + build: ['./build'] + dist: ['./dist'] + templates: ['./src/client/site/templates.js'] jade: pages: @@ -64,23 +69,26 @@ module.exports = (grunt)-> pretty: true files: [ expand: true - cwd: './src/jade' - src: '*.jade' - dest: './dist' - ext: '.html' + cwd: './src/client/site' + src: '**/index.jade' + dest: './build/static' + ext: '.html' ] - templates: options: client: true node: true - processName: (f)-> - f = f.replace './src/jade/templates/', '' - f = f.replace '.jade', '' - f = f.replace /\//g, '_' - return f + processName: (path)-> + pathElements = path.split '\/' + while true + element = pathElements.shift() + break if element is 'site' + pathElements.pop() + name = pathElements.join '/' + name = name.replace '.jade', '' + return name files: - './src/coffee/views.js': ['./src/jade/templates/**/*.jade'] + './src/client/site/templates.js': ['./src/client/site/**/!(index)*.jade'] mochaTest: options: @@ -89,28 +97,23 @@ module.exports = (grunt)-> reporter: 'dot' require: [ 'coffee-script/register' - './test/test_helper.coffee' + './src/test_helper.coffee' ] verbose: true - src: ['./test/**/*.test.coffee'] - - rsync: - static: - options: - src: './static/' - dest: './dist/' - recursive: true + src: ['./src/**/*.test.coffee'] sass: - build: + all: files: - './dist/css/main.css': ['./src/scss/main.scss'] - dist: - options: - sourcemap: 'none' - style: 'compressed' + './build/static/main.css': [ './build/imports.scss' ] + + sass_globbing: + all: files: - './dist/css/main.css': ['./src/scss/main.scss'] + './build/imports.scss': [ + './src/client/styles/main.scss' + './src/client/site/**/*.scss' + ] uglify: scripts: @@ -118,46 +121,114 @@ module.exports = (grunt)-> maxLineLen: 20 files: [ expand: true - cwd: './dist/js' + cwd: './build/static' src: '**/*.js' - dest: './dist/js' + dest: './build/static' ] watch: - static: - files: ['./static/**/*'] - tasks: ['rsync:static'] - coffee: - files: ['./src/**/*.coffee', './src/**/*.js'] - tasks: ['browserify:dev', 'exorcise'] - jade: - files: ['./src/**/*.jade'] - tasks: ['jade:pages', 'jade:templates'] + assets: + files: ['./assets/**/*'] + tasks: ['copy:assets_build'] + client_source: + files: ['./src/{client,common}/**/*.coffee'] + tasks: ['browserify:internal'] + server_source: + files: ['./src/{common,server}/**/*.coffee'] + tasks: ['copy:server_source'] + jade_pages: + files: ['./src/**/index.jade'] + tasks: ['jade:pages'] + jade_templates: + files: ['./src/**/!(index).jade'] + tasks: ['jade:templates', 'browserify:internal'] sass: files: ['./src/**/*.scss'] - tasks: ['sass', 'copy:styles'] + tasks: ['sass'] test: files: ['./src/**/*.coffee', './src/**/*.js', './test/**/*.coffee'] tasks: ['test'] - grunt.registerTask 'default', 'build' + # Compound Tasks ################################################################################################### - grunt.registerTask 'build', ['rsync', 'sass:build', 'jade', 'copy', 'browserify:dev', 'exorcise'] + grunt.registerTask 'build', ['jade', 'copy', 'css', 'browserify:external', 'browserify:internal'] - grunt.registerTask 'dist', ['rsync', 'sass:dist', 'jade', 'copy', 'browserify:prod', 'uglify'] + grunt.registerTask 'css', ['sass_globbing', 'sass'] + + grunt.registerTask 'default', ['clean', 'start'] + + grunt.registerTask 'deploy:prod', ['build', 'uglify', 'compress', 'copy:assets_dist', 'script:deploy:prod'] grunt.registerTask 'prepublish', ['clean', 'coffee'] + grunt.registerTask 'start', ['build', 'script:start'] + + grunt.registerTask 'test', ['mochaTest'] + + # Code Tasks ####################################################################################################### + + grunt.registerTask 'browserify:external', "Bundle 3rd-party libraries used in the app", -> + grunt.file.mkdir './build/static' + done = this.async() + + args = [].concat ("--require=#{lib}" for lib in EXTERNAL_LIBS), [ + '--outfile=./build/static/external.js' + ] + + options = cmd:'browserify', args:args + grunt.util.spawn options, (error)-> + console.log error if error? + done() + + grunt.registerTask 'browserify:internal', "Bundle source files needed in the browser", -> + grunt.file.mkdir './build/static' + done = this.async() + + libs = [] + for lib in EXTERNAL_LIBS + parts = lib.split ':' + libs.push parts[parts.length-1] + + args = [].concat ("--external=#{lib}" for lib in libs), [ + '--extension=.coffee' + '--outfile=./build/static/internal.js' + '--transform=coffeeify' + './src/client/client.coffee' + ] + + options = cmd:'browserify', args:args + grunt.util.spawn options, (error)-> + console.log error if error? + done() + grunt.registerTask 'use-local-deps', -> grunt.file.mkdir './node_modules' grunt.file.delete './node_modules/crafting-guide-common', force:true fs.symlinkSync '../../crafting-guide-common/', './node_modules/crafting-guide-common' - grunt.registerTask 'test', ['mochaTest'] + # Script Tasks ##################################################################################################### - grunt.registerTask 'watch-dev', ['clean', 'build', 'watch'] + grunt.registerTask 'script:deploy:prod', "deploy code by copying to the production branch", -> + done = this.async() + grunt.util.spawn cmd:'./scripts/deploy', args:['--production'], opts:{stdio:'inherit'}, -> done() - grunt.registerTask 'watch-test', ['clean', 'build', 'watch:test'] + grunt.registerTask 'script:deploy:staging', "deploy code by copying to the staging branch", -> + done = this.async() + grunt.util.spawn cmd:'./scripts/deploy', args:['--staging'], opts:{stdio:'inherit'}, -> done() + + grunt.registerTask 'publish', 'publishes this package to NPM', -> + done = this.async() + grunt.util.spawn cmd:'./scripts/publish', opts:{stdio:'inherit'}, -> done() + + grunt.registerTask 'script:s3_upload', 'uploads all static content to S3', -> + done = this.async() + grunt.util.spawn cmd:'./scripts/s3_upload', opts:{stdio:'inherit'}, -> done() + + grunt.registerTask 'script:start', "start the server at port 8080", -> + done = this.async() + grunt.util.spawn cmd:'./scripts/start', opts:{stdio:'inherit'}, -> done() + + # Command-Line Argument Processing ################################################################################# args = process.argv[..] while args.length > 0 diff --git a/assets/fonts/aller-regular.ttf b/assets/fonts/aller-regular.ttf new file mode 100755 index 000000000..40e9c69dc Binary files /dev/null and b/assets/fonts/aller-regular.ttf differ diff --git a/static/fonts/silkscreen.ttf b/assets/fonts/silkscreen.ttf similarity index 100% rename from static/fonts/silkscreen.ttf rename to assets/fonts/silkscreen.ttf diff --git a/static/google5a5af661c2ad567d.html b/assets/google5a5af661c2ad567d.html similarity index 100% rename from static/google5a5af661c2ad567d.html rename to assets/google5a5af661c2ad567d.html diff --git a/static/images/bedrock.png b/assets/images/bedrock.png similarity index 100% rename from static/images/bedrock.png rename to assets/images/bedrock.png diff --git a/assets/images/button-background-active.png b/assets/images/button-background-active.png new file mode 100644 index 000000000..f605b83be Binary files /dev/null and b/assets/images/button-background-active.png differ diff --git a/assets/images/button-background-hover.png b/assets/images/button-background-hover.png new file mode 100644 index 000000000..7960fbcb5 Binary files /dev/null and b/assets/images/button-background-hover.png differ diff --git a/assets/images/button-background-normal.png b/assets/images/button-background-normal.png new file mode 100644 index 000000000..2cfe84971 Binary files /dev/null and b/assets/images/button-background-normal.png differ diff --git a/assets/images/close.png b/assets/images/close.png new file mode 100644 index 000000000..8b7cbb50f Binary files /dev/null and b/assets/images/close.png differ diff --git a/static/images/empty.png b/assets/images/empty.png similarity index 100% rename from static/images/empty.png rename to assets/images/empty.png diff --git a/static/images/favicon.png b/assets/images/favicon.png similarity index 100% rename from static/images/favicon.png rename to assets/images/favicon.png diff --git a/static/images/github-login-large.png b/assets/images/github-login-large.png similarity index 100% rename from static/images/github-login-large.png rename to assets/images/github-login-large.png diff --git a/static/images/grass_side.png b/assets/images/grass_side.png similarity index 100% rename from static/images/grass_side.png rename to assets/images/grass_side.png diff --git a/static/images/ice.png b/assets/images/ice.png similarity index 100% rename from static/images/ice.png rename to assets/images/ice.png diff --git a/static/images/outline.png b/assets/images/outline.png similarity index 100% rename from static/images/outline.png rename to assets/images/outline.png diff --git a/assets/images/planks.png b/assets/images/planks.png new file mode 100644 index 000000000..ca51fb48c Binary files /dev/null and b/assets/images/planks.png differ diff --git a/assets/images/search.png b/assets/images/search.png new file mode 100644 index 000000000..2e9395903 Binary files /dev/null and b/assets/images/search.png differ diff --git a/static/images/workbench_front.png b/assets/images/site-icon.png similarity index 100% rename from static/images/workbench_front.png rename to assets/images/site-icon.png diff --git a/static/images/stone_brick.png b/assets/images/stone_brick.png similarity index 100% rename from static/images/stone_brick.png rename to assets/images/stone_brick.png diff --git a/static/images/unknown.png b/assets/images/unknown.png similarity index 100% rename from static/images/unknown.png rename to assets/images/unknown.png diff --git a/static/images/wait.gif b/assets/images/wait.gif similarity index 100% rename from static/images/wait.gif rename to assets/images/wait.gif diff --git a/static/robots.txt b/assets/robots.txt similarity index 100% rename from static/robots.txt rename to assets/robots.txt diff --git a/design/arrow.graffle b/design/arrow.graffle deleted file mode 100644 index 6b71e3ba3..000000000 Binary files a/design/arrow.graffle and /dev/null differ diff --git a/design/icons.graffle b/design/icons.graffle deleted file mode 100644 index 70622326e..000000000 Binary files a/design/icons.graffle and /dev/null differ diff --git a/design/iron_chests.graffle b/design/iron_chests.graffle deleted file mode 100644 index 8bc3673ce..000000000 Binary files a/design/iron_chests.graffle and /dev/null differ diff --git a/design/pages.graffle b/design/pages.graffle deleted file mode 100644 index 6516509e2..000000000 Binary files a/design/pages.graffle and /dev/null differ diff --git a/design/tutorial-scratchpad.graffle b/design/tutorial-scratchpad.graffle deleted file mode 100644 index 5fec5c951..000000000 Binary files a/design/tutorial-scratchpad.graffle and /dev/null differ diff --git a/design/v3/mobile-website.graffle/data.plist b/design/v3/mobile-website.graffle/data.plist deleted file mode 100644 index d4f93c093..000000000 --- a/design/v3/mobile-website.graffle/data.plist +++ /dev/null @@ -1,30866 +0,0 @@ - - - - - ApplicationVersion - - com.omnigroup.OmniGraffle.MacAppStore - 139.18 - - CreationDate - 2015-11-29 16:44:09 +0000 - Creator - Andrew Miner - GraphDocumentVersion - 8 - GuidesLocked - NO - GuidesVisible - YES - ImageCounter - 97 - ImageLinkBack - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - ImageList - - image96.tiff - image95.tiff - image94.tiff - image93.tiff - image92.tiff - image91.tiff - image86.tiff - image85.tiff - image84.tiff - image83.tiff - image82.tiff - image81.tiff - image79.tiff - image78.tiff - image77.tiff - image76.tiff - image75.tiff - image74.tiff - image73.tiff - image72.tiff - image71.tiff - image70.tiff - image69.tiff - image68.tiff - image67.tiff - image65.tiff - image64.tiff - image62.tiff - image61.tiff - image60.tiff - image59.tiff - image58.png - image54.png - image52.png - image51.png - image50.png - image49.png - image48.png - image46.tiff - image44.tiff - image43.tiff - image42.tiff - image41.tiff - image40.tiff - image39.png - image38.png - image37.png - image36.png - image35.png - image33.tiff - image31.tiff - image28.tiff - image27.tiff - image26.tiff - image25.tiff - image24.tiff - image23.tiff - image22.tiff - image21.tiff - image20.tiff - image18.tiff - image17.tiff - image16.tiff - image13.tiff - image12.tiff - image11.tiff - image10.tiff - image9.tiff - image8.tiff - image4.png - - LinksVisible - NO - MagnetsVisible - NO - MasterSheets - - ModificationDate - 2015-11-30 16:00:40 +0000 - Modifier - Andrew Miner - NotesVisible - NO - OriginVisible - NO - PageBreaks - NO - PrintInfo - - NSBottomMargin - - float - 41 - - NSHorizonalPagination - - coded - BAtzdHJlYW10eXBlZIHoA4QBQISEhAhOU051bWJlcgCEhAdOU1ZhbHVlAISECE5TT2JqZWN0AIWEASqEhAFxlwCG - - NSLeftMargin - - float - 18 - - NSPaperSize - - size - {611.99998474121094, 792} - - NSPrintReverseOrientation - - int - 0 - - NSRightMargin - - float - 18 - - NSTopMargin - - float - 18 - - - ReadOnly - NO - Sheets - - - ActiveLayerIndex - 0 - AutoAdjust - - BackgroundGraphic - - Bounds - {{0, 0}, {320, 752}} - Class - SolidGraphic - FontInfo - - Font - Helvetica-Bold - Size - 14 - - ID - 2 - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - BaseZoom - 0 - CanvasOrigin - {0, 0} - CanvasSize - {320, 752} - ColumnAlign - 1 - ColumnSpacing - 36 - DisplayScale - 1 pt = 1 px - GraphicsList - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 35011 - Layer - 0 - Points - - {160, 248} - {168, 264} - {152, 280} - {160, 296} - - Style - - stroke - - Color - - b - 0.580601 - g - 0.580591 - r - 0.580609 - - HeadArrow - SharpArrow - Legacy - - LineType - 1 - TailArrow - 0 - - - - - Bounds - {{24, 176}, {272, 80}} - Class - ShapedGraphic - FontInfo - - Color - - b - 0.584223 - g - 0.584213 - r - 0.58423 - - Font - HelveticaNeue - Size - 14 - - ID - 34994 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red149\green149\blue149;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 Click below for step by step instructions to make any item in Minecraft or your favorite mods.} - VerticalPad - 0 - - - - Bounds - {{185, 665}, {79, 30}} - Class - ShapedGraphic - ID - 34678 - ImageID - 44 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{61, 667}, {92, 26}} - Class - ShapedGraphic - ID - 34676 - ImageID - 43 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 536}, {304, 104}} - Class - ShapedGraphic - FontInfo - - Color - - b - 0.999991 - g - 0.999974 - r - 1 - - Font - InputMono-Black - Size - 14 - - ID - 34675 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf1 Crafting guide is a free, open-source project by Andrew Miner. It is the result of hundreds of hours of work. Contributions are gratefully appreciated!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{0, 720}, {320, 32}} - Class - ShapedGraphic - ID - 34674 - ImageID - 42 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{0, 528}, {320, 224}} - Class - ShapedGraphic - ID - 34673 - Layer - 0 - Link - - url - https://github.com/andrewminer/crafting-guide/fork - - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.0313725 - g - 0.0862745 - r - 0.180392 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 496}, {320, 32}} - Class - ShapedGraphic - ID - 34672 - ImageID - 41 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Class - Group - Graphics - - - Bounds - {{96, 304}, {144, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34998 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Add Item} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{70, 318}, {20, 4}} - Class - ShapedGraphic - ID - 35000 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{78, 310}, {4, 20}} - Class - ShapedGraphic - ID - 35001 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34999 - - - Bounds - {{72.000000000000028, 328}, {175.99999999999994, 8}} - Class - ShapedGraphic - ID - 35002 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{72.000000000000028, 304}, {175.99999999999994, 8}} - Class - ShapedGraphic - ID - 35003 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{72.000000000000028, 312}, {175.99999999999994, 16}} - Class - ShapedGraphic - ID - 35004 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{64, 312}, {8, 16}} - Class - ShapedGraphic - ID - 35005 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{64, 328}, {8, 8}} - Class - ShapedGraphic - ID - 35006 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{64, 304}, {8, 8}} - Class - ShapedGraphic - ID - 35007 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{248, 312}, {8, 16}} - Class - ShapedGraphic - ID - 35008 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{248, 328}, {8, 8}} - Class - ShapedGraphic - ID - 35009 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{248, 304}, {8, 8}} - Class - ShapedGraphic - ID - 35010 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34997 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 82}, {24, 4}} - Class - ShapedGraphic - ID - 34225 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 74}, {24, 4}} - Class - ShapedGraphic - ID - 34226 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 66}, {24, 4}} - Class - ShapedGraphic - ID - 34227 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34224 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 88}, {24, 8}} - Class - ShapedGraphic - ID - 34229 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 56}, {24, 8}} - Class - ShapedGraphic - ID - 34230 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 64}, {24, 24}} - Class - ShapedGraphic - ID - 34231 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34232 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34233 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34234 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34235 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34236 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34237 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34228 - Layer - 0 - - - Bounds - {{8, 120}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34202 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 Items to Craft} - VerticalPad - 0 - - - - Bounds - {{24, 56}, {96, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34163 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Craft} - VerticalPad - 0 - - - - Bounds - {{16, 64}, {112, 24}} - Class - ShapedGraphic - ID - 34201 - ImageID - 28 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 88}, {112, 8}} - Class - ShapedGraphic - ID - 34200 - ImageID - 27 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 56}, {112, 8}} - Class - ShapedGraphic - ID - 34199 - ImageID - 26 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34198 - ImageID - 25 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34197 - ImageID - 24 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34196 - ImageID - 23 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34195 - ImageID - 22 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34194 - ImageID - 21 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34193 - ImageID - 20 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{152, 56}, {96, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34164 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Search} - VerticalPad - 0 - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 34191 - Layer - 0 - Points - - {0, 48} - {320, 48} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{144, 88}, {112, 8}} - Class - ShapedGraphic - ID - 34190 - ImageID - 18 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{144, 56}, {112, 8}} - Class - ShapedGraphic - ID - 34188 - ImageID - 17 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{144, 64}, {112, 24}} - Class - ShapedGraphic - ID - 34186 - ImageID - 16 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34183 - ImageID - 13 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34182 - ImageID - 12 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34181 - ImageID - 11 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34180 - ImageID - 10 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34179 - ImageID - 9 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34178 - ImageID - 8 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 8}, {272, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 30 - - ID - 34161 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs60 \cf1 Crafting Guide} - VerticalPad - 0 - - - - Bounds - {{8, 8}, {32, 32}} - Class - ShapedGraphic - ID - 34160 - ImageID - 31 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 376}, {320, 100}} - Class - ShapedGraphic - ID - 34158 - ImageID - 62 - Layer - 0 - Shape - Rectangle - Style - - fill - - Color - - b - 0.6 - g - 0.6 - r - 0.6 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 0}, {320, 48}} - Class - ShapedGraphic - ID - 34162 - ImageID - 4 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 144}, {304, 208}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 34205 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{0, 0}, {320, 752}} - Class - ShapedGraphic - ID - 34901 - ImageID - 33 - Layer - 1 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - GridInfo - - GridSpacing - 8 - ShowsGrid - YES - SnapsToGrid - YES - - HPages - 1 - KeepToScale - - Layers - - - Lock - NO - Name - content - Print - YES - View - YES - - - Lock - YES - Name - background - Print - YES - View - YES - - - LayoutInfo - - Animate - NO - circoMinDist - 18 - circoSeparation - 0.0 - layoutEngine - dot - neatoSeparation - 0.0 - twopiSeparation - 0.0 - - Orientation - 2 - PrintOnePage - - RowAlign - 1 - RowSpacing - 36 - SheetTitle - Craft (empty) - UniqueID - 6 - VPages - 2 - - - ActiveLayerIndex - 2 - AutoAdjust - - BackgroundGraphic - - Bounds - {{0, 0}, {320, 480}} - Class - SolidGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 2 - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - BaseZoom - 0 - CanvasOrigin - {0, 0} - CanvasSize - {320, 480} - ColumnAlign - 1 - ColumnSpacing - 36 - DisplayScale - 1 pt = 1 px - GraphicsList - - - Bounds - {{56, 0}, {264, 55.017543859649123}} - Class - ShapedGraphic - FontInfo - - Color - - b - 0.753828 - g - 0.753798 - r - 0.753849 - - Font - InputMono-Black - Size - 25 - - ID - 35069 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 12 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red0\green0\blue0;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs50 \cf2 iron |} - - - - Bounds - {{8, 7.8596491228070136}, {24, 23.578947368421051}} - Class - ShapedGraphic - ID - 35064 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Circle - Style - - shadow - - Draws - NO - - stroke - - Width - 3 - - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 35065 - Layer - 0 - Points - - {24, 23.578947368421055} - {44, 43.228070175438589} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - Width - 6 - - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 35066 - Layer - 0 - Points - - {0, 55.017543859649109} - {320, 55.017543859649109} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 35067 - Layer - 0 - Points - - {0, 2.8421709430404007e-14} - {320, 2.8421709430404007e-14} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{0, 0}, {320, 55.017543859649123}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 25 - - ID - 35068 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 12 - - - - Bounds - {{0, 264}, {320, 216}} - Class - ShapedGraphic - ID - 4 - ImageID - 46 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 39 - Layer - 0 - Points - - {0, 276} - {320, 276} - - Style - - stroke - - Color - - b - 0.755581 - g - 0.755568 - r - 0.755591 - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{8, 220.01754385964909}, {32, 32}} - Class - ShapedGraphic - ID - 38 - ImageID - 52 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{48, 216.01754385964909}, {272, 40}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 37 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 12 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Iron Bars} - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 35 - Layer - 0 - Points - - {0, 216.01754385964909} - {320, 216.01754385964909} - - Style - - stroke - - Color - - b - 0.755581 - g - 0.755568 - r - 0.755591 - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{8, 180.01754385964909}, {32, 32}} - Class - ShapedGraphic - ID - 34 - ImageID - 51 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{48, 176.01754385964909}, {272, 40}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 33 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 12 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Iron Axe} - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 31 - Layer - 0 - Points - - {0, 176.01754385964909} - {320, 176.01754385964909} - - Style - - stroke - - Color - - b - 0.755581 - g - 0.755568 - r - 0.755591 - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{8, 140.01754385964909}, {32, 32}} - Class - ShapedGraphic - ID - 30 - ImageID - 50 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{48, 136.01754385964909}, {272, 40}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 29 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 12 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Glistering Melon} - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 27 - Layer - 0 - Points - - {0, 136.01754385964909} - {320, 136.01754385964909} - - Style - - stroke - - Color - - b - 0.755581 - g - 0.755568 - r - 0.755591 - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{8, 100.01754385964911}, {32, 32}} - Class - ShapedGraphic - ID - 26 - ImageID - 49 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{48, 96.017543859649109}, {272, 40}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 25 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 12 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Block of Iron} - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 14 - Layer - 0 - Points - - {0, 96.017543859649109} - {320, 96.017543859649109} - - Style - - stroke - - Color - - b - 0.755581 - g - 0.755568 - r - 0.755591 - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{8, 60.017543859649109}, {32, 32}} - Class - ShapedGraphic - ID - 13 - ImageID - 48 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{48, 56.017543859649109}, {272, 40}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 11 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 12 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Birch Wood Planks} - - - - Bounds - {{0, 0}, {320, 480}} - Class - ShapedGraphic - ID - 34909 - Layer - 1 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.95 - b - 1 - g - 1 - r - 1 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 0}, {320, 480}} - Class - ShapedGraphic - ID - 35070 - ImageID - 91 - Layer - 2 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - GridInfo - - GridSpacing - 4 - MajorGridSpacing - 16 - SnapsToGrid - YES - - HPages - 1 - KeepToScale - - Layers - - - Lock - NO - Name - popup - Print - YES - View - YES - - - Lock - YES - Name - screen - Print - YES - View - YES - - - Lock - YES - Name - background - Print - YES - View - YES - - - LayoutInfo - - Animate - NO - circoMinDist - 18 - circoSeparation - 0.0 - layoutEngine - dot - neatoSeparation - 0.0 - twopiSeparation - 0.0 - - Orientation - 2 - PrintOnePage - - RowAlign - 1 - RowSpacing - 36 - SheetTitle - Item Chooser - UniqueID - 3 - VPages - 1 - - - ActiveLayerIndex - 0 - AutoAdjust - - BackgroundGraphic - - Bounds - {{0, 0}, {320, 1888}} - Class - SolidGraphic - FontInfo - - Font - Helvetica-Bold - Size - 14 - - ID - 2 - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - BaseZoom - 0 - CanvasOrigin - {0, 0} - CanvasSize - {320, 1888} - ColumnAlign - 1 - ColumnSpacing - 36 - DisplayScale - 1 pt = 1 px - GraphicsList - - - Bounds - {{292, 60}, {16, 16}} - Class - ShapedGraphic - ID - 34993 - ImageID - 54 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.141442 - g - 0.070694 - r - 0.986343 - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Class - Group - Graphics - - - Bounds - {{16, 152}, {32, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34726 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs28 \cf2 16} - VerticalPad - 0 - - - - Bounds - {{24, 160}, {16, 16}} - Class - ShapedGraphic - ID - 34727 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{24, 176}, {16, 8}} - Class - ShapedGraphic - ID - 34728 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 160}, {8, 16}} - Class - ShapedGraphic - ID - 34729 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 176}, {8, 8}} - Class - ShapedGraphic - ID - 34730 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 152}, {8, 8}} - Class - ShapedGraphic - ID - 34731 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 160}, {8, 16}} - Class - ShapedGraphic - ID - 34732 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 176}, {8, 8}} - Class - ShapedGraphic - ID - 34733 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 152}, {8, 8}} - Class - ShapedGraphic - ID - 34734 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{24, 152}, {16, 8}} - Class - ShapedGraphic - ID - 34735 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34725 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{16, 192}, {32, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34737 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs28 \cf1 1} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{24, 216}, {16, 8}} - Class - ShapedGraphic - ID - 34739 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{24, 192}, {16, 8}} - Class - ShapedGraphic - ID - 34740 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{24, 200}, {16, 16}} - Class - ShapedGraphic - ID - 34741 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 200}, {8, 16}} - Class - ShapedGraphic - ID - 34742 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 216}, {8, 8}} - Class - ShapedGraphic - ID - 34743 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 192}, {8, 8}} - Class - ShapedGraphic - ID - 34744 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 200}, {8, 16}} - Class - ShapedGraphic - ID - 34745 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 216}, {8, 8}} - Class - ShapedGraphic - ID - 34746 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 192}, {8, 8}} - Class - ShapedGraphic - ID - 34747 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34738 - - - ID - 34736 - Layer - 0 - - - Bounds - {{185, 1785}, {79, 30}} - Class - ShapedGraphic - ID - 34678 - ImageID - 44 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{61, 1787}, {92, 26}} - Class - ShapedGraphic - ID - 34676 - ImageID - 43 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 1640}, {304, 104}} - Class - ShapedGraphic - FontInfo - - Color - - b - 0.999991 - g - 0.999974 - r - 1 - - Font - InputMono-Black - Size - 14 - - ID - 34675 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 Crafting guide is a free, open-source project by Andrew Miner. It is the result of hundreds of hours of work. Contributions are gratefully appreciated!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{0, 1856}, {320, 32}} - Class - ShapedGraphic - ID - 34674 - ImageID - 42 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{0, 1632}, {320, 224}} - Class - ShapedGraphic - ID - 34673 - Layer - 0 - Link - - url - https://github.com/andrewminer/crafting-guide/fork - - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.0313725 - g - 0.0862745 - r - 0.180392 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 1600}, {320, 32}} - Class - ShapedGraphic - ID - 34672 - ImageID - 41 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Class - Group - Graphics - - - Class - Group - Graphics - - - Bounds - {{278.00000184509224, 1427.0532042955397}, {12, 4}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34669 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{289.46410214776972, 1414.1249990774543}, {4, 20}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34670 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34668 - Rotation - 30 - - - Bounds - {{272, 1408}, {32, 32}} - Class - ShapedGraphic - ID - 34671 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34667 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 1432}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34658 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 1408}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34659 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 1416}, {15.999999999999993, 16}} - Class - ShapedGraphic - ID - 34660 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 1416}, {8, 16}} - Class - ShapedGraphic - ID - 34661 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 1432}, {8, 8}} - Class - ShapedGraphic - ID - 34662 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 1408}, {8, 8}} - Class - ShapedGraphic - ID - 34663 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 1416}, {8, 16}} - Class - ShapedGraphic - ID - 34664 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 1432}, {8, 8}} - Class - ShapedGraphic - ID - 34665 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 1408}, {8, 8}} - Class - ShapedGraphic - ID - 34666 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34657 - Layer - 0 - - - Class - Group - Graphics - - - Class - Group - Graphics - - - Bounds - {{278.00000184509224, 1243.0532042955397}, {12, 4}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34654 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{289.46410214776972, 1230.1249990774543}, {4, 20}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34655 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34653 - Rotation - 30 - - - Bounds - {{272, 1224}, {32, 32}} - Class - ShapedGraphic - ID - 34656 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34652 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 1248}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34643 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 1224}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34644 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 1232}, {15.999999999999993, 16}} - Class - ShapedGraphic - ID - 34645 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 1232}, {8, 16}} - Class - ShapedGraphic - ID - 34646 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 1248}, {8, 8}} - Class - ShapedGraphic - ID - 34647 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 1224}, {8, 8}} - Class - ShapedGraphic - ID - 34648 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 1232}, {8, 16}} - Class - ShapedGraphic - ID - 34649 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 1248}, {8, 8}} - Class - ShapedGraphic - ID - 34650 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 1224}, {8, 8}} - Class - ShapedGraphic - ID - 34651 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34642 - Layer - 0 - - - Class - Group - Graphics - - - Class - Group - Graphics - - - Bounds - {{278.00000184509224, 1059.0532042955397}, {12, 4}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34634 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{289.46410214776972, 1046.1249990774543}, {4, 20}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34635 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34633 - Rotation - 30 - - - Bounds - {{272, 1040}, {32, 32}} - Class - ShapedGraphic - ID - 34636 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34632 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 1064}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34623 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 1040}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34624 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 1048}, {15.999999999999993, 16}} - Class - ShapedGraphic - ID - 34625 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 1048}, {8, 16}} - Class - ShapedGraphic - ID - 34626 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 1064}, {8, 8}} - Class - ShapedGraphic - ID - 34627 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 1040}, {8, 8}} - Class - ShapedGraphic - ID - 34628 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 1048}, {8, 16}} - Class - ShapedGraphic - ID - 34629 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 1064}, {8, 8}} - Class - ShapedGraphic - ID - 34630 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 1040}, {8, 8}} - Class - ShapedGraphic - ID - 34631 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34622 - Layer - 0 - - - Class - Group - Graphics - - - Class - Group - Graphics - - - Bounds - {{278.00000184509224, 635.05320429553967}, {12, 4}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34619 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{289.46410214776972, 622.12499907745416}, {4, 20}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34620 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34618 - Rotation - 30 - - - Bounds - {{272, 616}, {32, 32}} - Class - ShapedGraphic - ID - 34621 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34617 - Layer - 0 - - - Class - Group - Graphics - - - Class - Group - Graphics - - - Bounds - {{278.00000184509224, 675.05320429553967}, {12, 4}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34614 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{289.46410214776972, 662.12499907745416}, {4, 20}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34615 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34613 - Rotation - 30 - - - Bounds - {{272, 656}, {32, 32}} - Class - ShapedGraphic - ID - 34616 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34612 - Layer - 0 - - - Class - Group - Graphics - - - Class - Group - Graphics - - - Bounds - {{278.00000184509224, 899.05320429553967}, {12, 4}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34609 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{289.46410214776972, 886.12499907745416}, {4, 20}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 15 - - ID - 34610 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Rotation - 30 - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34608 - Rotation - 30 - - - Bounds - {{272, 880}, {32, 32}} - Class - ShapedGraphic - ID - 34611 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34607 - Layer - 0 - - - Bounds - {{72, 1512}, {32, 32}} - Class - ShapedGraphic - ID - 34587 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{72, 1480}, {32, 32}} - Class - ShapedGraphic - ID - 34586 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{104, 1512}, {32, 32}} - Class - ShapedGraphic - ID - 34585 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{104, 1480}, {32, 32}} - Class - ShapedGraphic - ID - 34584 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{136, 1512}, {32, 32}} - Class - ShapedGraphic - ID - 34583 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{136, 1480}, {32, 32}} - Class - ShapedGraphic - ID - 34582 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{72, 1448}, {32, 32}} - Class - ShapedGraphic - ID - 34580 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{24, 1544}, {192, 24}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 12 - - ID - 34565 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs24 \cf0 Crafting Table} - VerticalPad - 0 - - - - Bounds - {{216, 1480}, {32, 32}} - Class - ShapedGraphic - ID - 34563 - ImageID - 36 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{216, 1480}, {32, 32}} - Class - ShapedGraphic - ID - 34562 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{56, 1408}, {32, 32}} - Class - ShapedGraphic - ID - 34561 - ImageID - 36 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 1408}, {32, 32}} - Class - ShapedGraphic - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34560 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf0 4.} - VerticalPad - 0 - - - - Bounds - {{96, 1408}, {160, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34559 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Iron Chestplate} - VerticalPad - 0 - - - - Bounds - {{136, 1448}, {32, 32}} - Class - ShapedGraphic - ID - 34558 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{72, 1512}, {32, 32}} - Class - ShapedGraphic - ID - 34557 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 1512}, {32, 32}} - Class - ShapedGraphic - ID - 34556 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 1512}, {32, 32}} - Class - ShapedGraphic - ID - 34555 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{72, 1480}, {32, 32}} - Class - ShapedGraphic - ID - 34554 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 1480}, {32, 32}} - Class - ShapedGraphic - ID - 34553 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 1480}, {32, 32}} - Class - ShapedGraphic - ID - 34552 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{72, 1448}, {32, 32}} - Class - ShapedGraphic - ID - 34551 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 1448}, {32, 32}} - Class - ShapedGraphic - ID - 34550 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 1448}, {32, 32}} - Class - ShapedGraphic - ID - 34549 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 34548 - Layer - 0 - Points - - {8.0000000000000284, 1400} - {312, 1400} - - Style - - stroke - - Color - - a - 0.25 - b - 0 - g - 0 - r - 0 - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{0, 304}, {320, 100}} - Class - ShapedGraphic - ID - 34547 - ImageID - 64 - Layer - 0 - Shape - Rectangle - Style - - fill - - Color - - b - 0.6 - g - 0.6 - r - 0.6 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{104, 1328}, {32, 32}} - Class - ShapedGraphic - ID - 34546 - ImageID - 40 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{104, 1264}, {32, 32}} - Class - ShapedGraphic - ID - 34545 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Class - Group - Graphics - - - Bounds - {{280, 904}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34596 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 880}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34597 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 888}, {15.999999999999993, 16}} - Class - ShapedGraphic - ID - 34598 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 888}, {8, 16}} - Class - ShapedGraphic - ID - 34599 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 904}, {8, 8}} - Class - ShapedGraphic - ID - 34600 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 880}, {8, 8}} - Class - ShapedGraphic - ID - 34601 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 888}, {8, 16}} - Class - ShapedGraphic - ID - 34602 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 904}, {8, 8}} - Class - ShapedGraphic - ID - 34603 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 880}, {8, 8}} - Class - ShapedGraphic - ID - 34604 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34595 - Layer - 0 - - - Bounds - {{200, 1328}, {64, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34492 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf0 x16} - VerticalPad - 0 - - - - Bounds - {{24, 1360}, {192, 24}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 12 - - ID - 34491 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs24 \cf0 Crafting Table} - VerticalPad - 0 - - - - Bounds - {{216, 1296}, {32, 32}} - Class - ShapedGraphic - ID - 34489 - ImageID - 35 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{216, 1296}, {32, 32}} - Class - ShapedGraphic - ID - 34488 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{56, 1224}, {32, 32}} - Class - ShapedGraphic - ID - 34487 - ImageID - 35 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 1224}, {32, 32}} - Class - ShapedGraphic - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34486 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf0 3.} - VerticalPad - 0 - - - - Bounds - {{96, 1224}, {160, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34485 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Iron Sword} - VerticalPad - 0 - - - - Bounds - {{104, 1296}, {32, 32}} - Class - ShapedGraphic - ID - 34484 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{72, 1328}, {32, 32}} - Class - ShapedGraphic - ID - 34483 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 1328}, {32, 32}} - Class - ShapedGraphic - ID - 34482 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 1328}, {32, 32}} - Class - ShapedGraphic - ID - 34481 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{72, 1296}, {32, 32}} - Class - ShapedGraphic - ID - 34480 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 1296}, {32, 32}} - Class - ShapedGraphic - ID - 34479 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 1296}, {32, 32}} - Class - ShapedGraphic - ID - 34478 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{72, 1264}, {32, 32}} - Class - ShapedGraphic - ID - 34477 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 1264}, {32, 32}} - Class - ShapedGraphic - ID - 34476 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 1264}, {32, 32}} - Class - ShapedGraphic - ID - 34475 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 34474 - Layer - 0 - Points - - {8.0000000000000284, 1216} - {312, 1216} - - Style - - stroke - - Color - - a - 0.25 - b - 0 - g - 0 - r - 0 - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{200, 1144}, {64, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34473 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf0 x3} - VerticalPad - 0 - - - - Bounds - {{24, 1176}, {192, 24}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 12 - - ID - 34472 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs24 \cf0 Precision Sawmill} - VerticalPad - 0 - - - - Bounds - {{232, 1128}, {15.999999999999993, 16}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - w - 1 - - Font - Silkscreen - Size - 14 - - ID - 34471 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Beneath - YES - Fuzziness - 0.71917462348937988 - ShadowVector - {1, 1} - - stroke - - Draws - NO - - - Text - - Align - 2 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qr - -\f0\fs28 \cf1 6} - VerticalPad - 0 - - TextPlacement - 2 - Wrap - NO - - - Bounds - {{216, 1112}, {32, 32}} - Class - ShapedGraphic - ID - 34470 - ImageID - 40 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{216, 1112}, {32, 32}} - Class - ShapedGraphic - ID - 34469 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{56, 1040}, {32, 32}} - Class - ShapedGraphic - ID - 34468 - ImageID - 40 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 1040}, {32, 32}} - Class - ShapedGraphic - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34467 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf0 2.} - VerticalPad - 0 - - - - Bounds - {{96, 1040}, {160, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34466 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Stick} - VerticalPad - 0 - - - - Bounds - {{104, 1112}, {32, 32}} - Class - ShapedGraphic - ID - 34465 - ImageID - 39 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{72, 1144}, {32, 32}} - Class - ShapedGraphic - ID - 34464 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 1144}, {32, 32}} - Class - ShapedGraphic - ID - 34463 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 1144}, {32, 32}} - Class - ShapedGraphic - ID - 34462 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{72, 1112}, {32, 32}} - Class - ShapedGraphic - ID - 34461 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 1112}, {32, 32}} - Class - ShapedGraphic - ID - 34460 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 1112}, {32, 32}} - Class - ShapedGraphic - ID - 34459 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{72, 1080}, {32, 32}} - Class - ShapedGraphic - ID - 34458 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 1080}, {32, 32}} - Class - ShapedGraphic - ID - 34457 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 1080}, {32, 32}} - Class - ShapedGraphic - ID - 34456 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 34455 - Layer - 0 - Points - - {8.0000000000000284, 1032} - {312, 1032} - - Style - - stroke - - Color - - a - 0.25 - b - 0 - g - 0 - r - 0 - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{232, 968}, {15.999999999999993, 16}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - w - 1 - - Font - Silkscreen - Size - 14 - - ID - 34454 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Beneath - YES - Fuzziness - 0.71917462348937988 - ShadowVector - {1, 1} - - stroke - - Draws - NO - - - Text - - Align - 2 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qr - -\f0\fs28 \cf1 4} - VerticalPad - 0 - - TextPlacement - 2 - Wrap - NO - - - Bounds - {{216, 952}, {32, 32}} - Class - ShapedGraphic - ID - 34452 - ImageID - 39 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{216, 952}, {32, 32}} - Class - ShapedGraphic - ID - 34447 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{56, 880}, {32, 32}} - Class - ShapedGraphic - ID - 34442 - ImageID - 39 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 880}, {32, 32}} - Class - ShapedGraphic - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34441 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf0 1.} - VerticalPad - 0 - - - - Bounds - {{96, 880}, {160, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34440 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Oak Wood Planks} - VerticalPad - 0 - - - - Bounds - {{104, 952}, {32, 32}} - Class - ShapedGraphic - ID - 34429 - ImageID - 38 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{72, 984}, {32, 32}} - Class - ShapedGraphic - ID - 34438 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 984}, {32, 32}} - Class - ShapedGraphic - ID - 34437 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 984}, {32, 32}} - Class - ShapedGraphic - ID - 34436 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{72, 952}, {32, 32}} - Class - ShapedGraphic - ID - 34435 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 952}, {32, 32}} - Class - ShapedGraphic - ID - 34434 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 952}, {32, 32}} - Class - ShapedGraphic - ID - 34433 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{72, 920}, {32, 32}} - Class - ShapedGraphic - ID - 34432 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{104, 920}, {32, 32}} - Class - ShapedGraphic - ID - 34431 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{136, 920}, {32, 32}} - Class - ShapedGraphic - ID - 34430 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Color - - b - 0.191158 - g - 0.191155 - r - 0.191161 - - - - - - Bounds - {{8, 872}, {304, 712}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 34428 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 848}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34427 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 STEPS} - VerticalPad - 0 - - - - Bounds - {{280, 680}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34497 - ImageID - 18 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 656}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34498 - ImageID - 17 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 664}, {15.999999999999993, 16}} - Class - ShapedGraphic - ID - 34499 - ImageID - 16 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 664}, {8, 16}} - Class - ShapedGraphic - ID - 34500 - ImageID - 10 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 680}, {8, 8}} - Class - ShapedGraphic - ID - 34501 - ImageID - 9 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 656}, {8, 8}} - Class - ShapedGraphic - ID - 34502 - ImageID - 8 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 664}, {8, 16}} - Class - ShapedGraphic - ID - 34503 - ImageID - 13 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 680}, {8, 8}} - Class - ShapedGraphic - ID - 34504 - ImageID - 12 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 656}, {8, 8}} - Class - ShapedGraphic - ID - 34505 - ImageID - 11 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 640}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34410 - ImageID - 18 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 616}, {15.999999999999993, 8}} - Class - ShapedGraphic - ID - 34409 - ImageID - 17 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 624}, {15.999999999999993, 16}} - Class - ShapedGraphic - ID - 34408 - ImageID - 16 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 624}, {8, 16}} - Class - ShapedGraphic - ID - 34407 - ImageID - 10 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 640}, {8, 8}} - Class - ShapedGraphic - ID - 34406 - ImageID - 9 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 616}, {8, 8}} - Class - ShapedGraphic - ID - 34405 - ImageID - 8 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 624}, {8, 16}} - Class - ShapedGraphic - ID - 34404 - ImageID - 13 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 640}, {8, 8}} - Class - ShapedGraphic - ID - 34403 - ImageID - 12 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 616}, {8, 8}} - Class - ShapedGraphic - ID - 34402 - ImageID - 11 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 656}, {32, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34399 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs28 \cf0 1} - VerticalPad - 0 - - - - Bounds - {{96, 656}, {160, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34398 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Oak Wood} - VerticalPad - 0 - - - - Bounds - {{56, 656}, {32, 32}} - Class - ShapedGraphic - ID - 34397 - ImageID - 38 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 616}, {32, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34396 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs28 \cf0 40} - VerticalPad - 0 - - - - Bounds - {{96, 616}, {160, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34395 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Iron Ingot} - VerticalPad - 0 - - - - Bounds - {{56, 616}, {32, 32}} - Class - ShapedGraphic - ID - 34394 - ImageID - 37 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 600}, {304, 104}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 34393 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 576}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34392 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 NEED TO GATHER} - VerticalPad - 0 - - - - Bounds - {{24, 464}, {272, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.584223 - g - 0.584213 - r - 0.58423 - - Font - Silkscreen - Size - 20 - - ID - 34391 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;\red149\green149\blue149;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf2 Nothing yet} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{96, 512}, {144, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34763 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Add Item} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{70, 526}, {20, 4}} - Class - ShapedGraphic - ID - 34765 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{78, 518}, {4, 20}} - Class - ShapedGraphic - ID - 34766 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34764 - - - Bounds - {{72.000000000000028, 536}, {175.99999999999994, 8}} - Class - ShapedGraphic - ID - 34767 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{72.000000000000028, 512}, {175.99999999999994, 8}} - Class - ShapedGraphic - ID - 34768 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{72.000000000000028, 520}, {175.99999999999994, 16}} - Class - ShapedGraphic - ID - 34769 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{64, 520}, {8, 16}} - Class - ShapedGraphic - ID - 34770 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{64, 536}, {8, 8}} - Class - ShapedGraphic - ID - 34771 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{64, 512}, {8, 8}} - Class - ShapedGraphic - ID - 34772 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{248, 520}, {8, 16}} - Class - ShapedGraphic - ID - 34773 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{248, 536}, {8, 8}} - Class - ShapedGraphic - ID - 34774 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{248, 512}, {8, 8}} - Class - ShapedGraphic - ID - 34775 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34762 - Layer - 0 - - - Bounds - {{8, 448}, {304, 104}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 34349 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 424}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34348 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 ALREADY HAVE} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{278, 206}, {20, 4}} - Class - ShapedGraphic - ID - 34338 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.141442 - g - 0.070694 - r - 0.986343 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 216}, {16, 8}} - Class - ShapedGraphic - ID - 34339 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 192}, {16, 8}} - Class - ShapedGraphic - ID - 34340 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 200}, {16, 16}} - Class - ShapedGraphic - ID - 34341 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 200}, {8, 16}} - Class - ShapedGraphic - ID - 34342 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 216}, {8, 8}} - Class - ShapedGraphic - ID - 34343 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 192}, {8, 8}} - Class - ShapedGraphic - ID - 34344 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 200}, {8, 16}} - Class - ShapedGraphic - ID - 34345 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 216}, {8, 8}} - Class - ShapedGraphic - ID - 34346 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 192}, {8, 8}} - Class - ShapedGraphic - ID - 34347 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34337 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{278, 166}, {20, 4}} - Class - ShapedGraphic - ID - 34327 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.141442 - g - 0.070694 - r - 0.986343 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 176}, {16, 8}} - Class - ShapedGraphic - ID - 34328 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 152}, {16, 8}} - Class - ShapedGraphic - ID - 34329 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 160}, {16, 16}} - Class - ShapedGraphic - ID - 34330 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 160}, {8, 16}} - Class - ShapedGraphic - ID - 34331 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 176}, {8, 8}} - Class - ShapedGraphic - ID - 34332 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 152}, {8, 8}} - Class - ShapedGraphic - ID - 34333 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 160}, {8, 16}} - Class - ShapedGraphic - ID - 34334 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 176}, {8, 8}} - Class - ShapedGraphic - ID - 34335 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{296, 152}, {8, 8}} - Class - ShapedGraphic - ID - 34336 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34326 - Layer - 0 - - - Bounds - {{96, 192}, {160, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34310 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Iron Chestplate} - VerticalPad - 0 - - - - Bounds - {{56, 192}, {32, 32}} - Class - ShapedGraphic - ID - 34309 - ImageID - 36 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Class - Group - Graphics - - - Bounds - {{96, 240}, {144, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34749 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Add Item} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{70, 254}, {20, 4}} - Class - ShapedGraphic - ID - 34751 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{78, 246}, {4, 20}} - Class - ShapedGraphic - ID - 34752 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.150712 - g - 0.825267 - r - 0.289744 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34750 - - - Bounds - {{72.000000000000028, 264}, {175.99999999999994, 8}} - Class - ShapedGraphic - ID - 34753 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{72.000000000000028, 240}, {175.99999999999994, 8}} - Class - ShapedGraphic - ID - 34754 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{72.000000000000028, 248}, {175.99999999999994, 16}} - Class - ShapedGraphic - ID - 34755 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{64, 248}, {8, 16}} - Class - ShapedGraphic - ID - 34756 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{64, 264}, {8, 8}} - Class - ShapedGraphic - ID - 34757 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{64, 240}, {8, 8}} - Class - ShapedGraphic - ID - 34758 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{248, 248}, {8, 16}} - Class - ShapedGraphic - ID - 34759 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{248, 264}, {8, 8}} - Class - ShapedGraphic - ID - 34760 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{248, 240}, {8, 8}} - Class - ShapedGraphic - ID - 34761 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34748 - Layer - 0 - - - Bounds - {{96, 152}, {160, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34239 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf0 Iron Sword} - VerticalPad - 0 - - - - Bounds - {{56, 152}, {32, 32}} - Class - ShapedGraphic - ID - 34238 - ImageID - 35 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Class - Group - Graphics - - - Bounds - {{280, 82}, {24, 4}} - Class - ShapedGraphic - ID - 34225 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 74}, {24, 4}} - Class - ShapedGraphic - ID - 34226 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 66}, {24, 4}} - Class - ShapedGraphic - ID - 34227 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34224 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 88}, {24, 8}} - Class - ShapedGraphic - ID - 34229 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 56}, {24, 8}} - Class - ShapedGraphic - ID - 34230 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 64}, {24, 24}} - Class - ShapedGraphic - ID - 34231 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34232 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34233 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34234 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34235 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34236 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34237 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34228 - Layer - 0 - - - Bounds - {{8, 120}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34202 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 Items to Craft} - VerticalPad - 0 - - - - Bounds - {{24, 56}, {96, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34163 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Craft} - VerticalPad - 0 - - - - Bounds - {{16, 64}, {112, 24}} - Class - ShapedGraphic - ID - 34201 - ImageID - 28 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 88}, {112, 8}} - Class - ShapedGraphic - ID - 34200 - ImageID - 27 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 56}, {112, 8}} - Class - ShapedGraphic - ID - 34199 - ImageID - 26 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34198 - ImageID - 25 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34197 - ImageID - 24 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34196 - ImageID - 23 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34195 - ImageID - 22 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34194 - ImageID - 21 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34193 - ImageID - 20 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{152, 56}, {96, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34164 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Search} - VerticalPad - 0 - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 34191 - Layer - 0 - Points - - {0, 48} - {320, 48} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{144, 88}, {112, 8}} - Class - ShapedGraphic - ID - 34190 - ImageID - 18 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{144, 56}, {112, 8}} - Class - ShapedGraphic - ID - 34188 - ImageID - 17 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{144, 64}, {112, 24}} - Class - ShapedGraphic - ID - 34186 - ImageID - 16 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34183 - ImageID - 13 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34182 - ImageID - 12 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34181 - ImageID - 11 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34180 - ImageID - 10 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34179 - ImageID - 9 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34178 - ImageID - 8 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 8}, {272, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 30 - - ID - 34161 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs60 \cf1 Crafting Guide} - VerticalPad - 0 - - - - Bounds - {{8, 8}, {32, 32}} - Class - ShapedGraphic - ID - 34160 - ImageID - 31 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 724}, {320, 100}} - Class - ShapedGraphic - ID - 34158 - ImageID - 65 - Layer - 0 - Shape - Rectangle - Style - - fill - - Color - - b - 0.6 - g - 0.6 - r - 0.6 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 0}, {320, 48}} - Class - ShapedGraphic - ID - 34162 - ImageID - 4 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 144}, {304, 136}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 34205 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{0, 0}, {320, 1888}} - Class - ShapedGraphic - ID - 34204 - ImageID - 33 - Layer - 1 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - GridInfo - - GridSpacing - 4 - MajorGridColor - - a - 0.8 - b - 0.0520873 - g - 1 - r - 0.392612 - - MajorGridSpacing - 16 - MinorGridColor - - a - 0.4 - b - 0.0520873 - g - 1 - r - 0.392612 - - ShowsGrid - YES - SnapsToGrid - YES - - HPages - 1 - KeepToScale - - Layers - - - Lock - NO - Name - content - Print - YES - View - YES - - - Lock - YES - Name - background - Print - YES - View - YES - - - LayoutInfo - - Animate - NO - circoMinDist - 18 - circoSeparation - 0.0 - layoutEngine - dot - neatoSeparation - 0.0 - twopiSeparation - 0.0 - - Orientation - 2 - PrintOnePage - - RowAlign - 1 - RowSpacing - 36 - SheetTitle - Craft (with steps) - UniqueID - 2 - VPages - 3 - - - ActiveLayerIndex - 2 - AutoAdjust - - BackgroundGraphic - - Bounds - {{0, 0}, {320, 480}} - Class - SolidGraphic - FontInfo - - Font - Helvetica-Bold - Size - 14 - - ID - 2 - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - BaseZoom - 0 - CanvasOrigin - {0, 0} - CanvasSize - {320, 480} - ColumnAlign - 1 - ColumnSpacing - 36 - DisplayScale - 1 pt = 1 px - GraphicsList - - - Bounds - {{48, 96}, {224, 48}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 25 - - ID - 34926 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red0\green0\blue0;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs50 \cf2 16|} - VerticalPad - 0 - - - - Bounds - {{16, 96}, {288, 56.000000000000625}} - Class - ShapedGraphic - ID - 34925 - Layer - 0 - Magnets - - {-0.18661591403774672, 1.3202093158143569} - {1.3181773861806965, 0.20046426385991356} - {0.10935995984547869, -1.3288408819079482} - - Shape - Bezier - ShapeData - - UnitPoints - - {-0.44444444444444525, 0.5} - {-0.44444444444444525, 0.5} - {-0.47222222222222293, 0.35714285714284477} - {-0.47222222222222293, 0.35714285714284477} - {-0.47222222222222293, 0.35714285714284477} - {-0.49999999999999944, 0.35714285714284477} - {-0.49999999999999944, 0.35714285714284477} - {-0.49999999999999944, 0.35714285714284477} - {-0.5, -0.5} - {-0.5, -0.5} - {-0.5, -0.50000000000000133} - {0.5, -0.49999999999999689} - {0.5, -0.5} - {0.5, -0.49999999999999689} - {0.5, 0.35714285714284477} - {0.5, 0.35714285714284477} - {0.5, 0.35714285714284477} - {-0.41666666666666785, 0.35714285714284477} - {-0.41666666666666785, 0.35714285714284477} - {-0.41666666666666785, 0.35714285714284477} - {-0.44444444444444525, 0.5} - - - - - Bounds - {{0, 264}, {320, 216}} - Class - ShapedGraphic - ID - 4 - ImageID - 46 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 152}, {32, 32}} - Class - ShapedGraphic - FontInfo - - Font - HelveticaNeue - Size - 14 - - ID - 34924 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs28 \cf1 16} - VerticalPad - 0 - - - - Bounds - {{24, 160}, {16, 16}} - Class - ShapedGraphic - ID - 34923 - ImageID - 16 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{24, 176}, {16, 8}} - Class - ShapedGraphic - ID - 34922 - ImageID - 18 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 160}, {8, 16}} - Class - ShapedGraphic - ID - 34921 - ImageID - 10 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 176}, {8, 8}} - Class - ShapedGraphic - ID - 34920 - ImageID - 9 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 152}, {8, 8}} - Class - ShapedGraphic - ID - 34919 - ImageID - 8 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 160}, {8, 16}} - Class - ShapedGraphic - ID - 34918 - ImageID - 13 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 176}, {8, 8}} - Class - ShapedGraphic - ID - 34917 - ImageID - 12 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 152}, {8, 8}} - Class - ShapedGraphic - ID - 34916 - ImageID - 11 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{24, 152}, {16, 8}} - Class - ShapedGraphic - ID - 34915 - ImageID - 17 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{0, 0}, {320, 480}} - Class - ShapedGraphic - ID - 34909 - Layer - 1 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.8 - b - 0.999991 - g - 0.999974 - r - 1 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 0}, {320, 480}} - Class - ShapedGraphic - ID - 34932 - ImageID - 92 - Layer - 2 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - GridInfo - - GridSpacing - 8 - ShowsGrid - YES - SnapsToGrid - YES - - HPages - 1 - KeepToScale - - Layers - - - Lock - NO - Name - pop-up - Print - YES - View - YES - - - Lock - YES - Name - screen - Print - YES - View - YES - - - Lock - YES - Name - content - Print - YES - View - YES - - - LayoutInfo - - Animate - NO - circoMinDist - 18 - circoSeparation - 0.0 - layoutEngine - dot - neatoSeparation - 0.0 - twopiSeparation - 0.0 - - Orientation - 2 - PrintOnePage - - RowAlign - 1 - RowSpacing - 36 - SheetTitle - Quantity Chooser - UniqueID - 4 - VPages - 1 - - - ActiveLayerIndex - 2 - AutoAdjust - - BackgroundGraphic - - Bounds - {{0, 0}, {320, 480}} - Class - SolidGraphic - FontInfo - - Font - Helvetica-Bold - Size - 14 - - ID - 2 - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - BaseZoom - 0 - CanvasOrigin - {0, 0} - CanvasSize - {320, 480} - ColumnAlign - 1 - ColumnSpacing - 36 - DisplayScale - 1 pt = 1 px - GraphicsList - - - Bounds - {{64, 56}, {192, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34163 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Craft} - VerticalPad - 0 - - - - Bounds - {{56, 64}, {208, 24}} - Class - ShapedGraphic - ID - 34201 - ImageID - 28 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{56, 88}, {208, 8}} - Class - ShapedGraphic - ID - 34200 - ImageID - 27 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{56, 56}, {208, 8}} - Class - ShapedGraphic - ID - 34199 - ImageID - 26 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34198 - ImageID - 25 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34197 - ImageID - 24 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34196 - ImageID - 23 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34195 - ImageID - 22 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34194 - ImageID - 21 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34193 - ImageID - 20 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{64, 96}, {192, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35033 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Search} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{56, 128}, {208, 8}} - Class - ShapedGraphic - ID - 35024 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 96}, {208, 8}} - Class - ShapedGraphic - ID - 35025 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{56, 104}, {208, 24}} - Class - ShapedGraphic - ID - 35026 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 104}, {8, 24}} - Class - ShapedGraphic - ID - 35027 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 128}, {8, 8}} - Class - ShapedGraphic - ID - 35028 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 96}, {8, 8}} - Class - ShapedGraphic - ID - 35029 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 104}, {8, 24}} - Class - ShapedGraphic - ID - 35030 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 128}, {8, 8}} - Class - ShapedGraphic - ID - 35031 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 96}, {8, 8}} - Class - ShapedGraphic - ID - 35032 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 35023 - Layer - 0 - - - Bounds - {{64, 296}, {192, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35006 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Feedback} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{56, 328}, {208, 8}} - Class - ShapedGraphic - ID - 34997 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 296}, {208, 8}} - Class - ShapedGraphic - ID - 34998 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{56, 304}, {208, 24}} - Class - ShapedGraphic - ID - 34999 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 304}, {8, 24}} - Class - ShapedGraphic - ID - 35000 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 328}, {8, 8}} - Class - ShapedGraphic - ID - 35001 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 296}, {8, 8}} - Class - ShapedGraphic - ID - 35002 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 304}, {8, 24}} - Class - ShapedGraphic - ID - 35003 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 328}, {8, 8}} - Class - ShapedGraphic - ID - 35004 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 296}, {8, 8}} - Class - ShapedGraphic - ID - 35005 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34996 - Layer - 0 - - - Bounds - {{252, 140}, {16, 16}} - Class - ShapedGraphic - ID - 34994 - ImageID - 54 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.141442 - g - 0.070694 - r - 0.986343 - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{292, 60}, {16, 16}} - Class - ShapedGraphic - ID - 34993 - ImageID - 54 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.141442 - g - 0.070694 - r - 0.986343 - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{64, 256}, {192, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34991 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Login} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{56, 288}, {208, 8}} - Class - ShapedGraphic - ID - 34982 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 256}, {208, 8}} - Class - ShapedGraphic - ID - 34983 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{56, 264}, {208, 24}} - Class - ShapedGraphic - ID - 34984 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 264}, {8, 24}} - Class - ShapedGraphic - ID - 34985 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 288}, {8, 8}} - Class - ShapedGraphic - ID - 34986 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 256}, {8, 8}} - Class - ShapedGraphic - ID - 34987 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 264}, {8, 24}} - Class - ShapedGraphic - ID - 34988 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 288}, {8, 8}} - Class - ShapedGraphic - ID - 34989 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 256}, {8, 8}} - Class - ShapedGraphic - ID - 34990 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34981 - Layer - 0 - - - Bounds - {{64, 216}, {192, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34980 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 SHARE} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{56, 248}, {208, 8}} - Class - ShapedGraphic - ID - 34971 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 216}, {208, 8}} - Class - ShapedGraphic - ID - 34972 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{56, 224}, {208, 24}} - Class - ShapedGraphic - ID - 34973 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 224}, {8, 24}} - Class - ShapedGraphic - ID - 34974 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 248}, {8, 8}} - Class - ShapedGraphic - ID - 34975 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 216}, {8, 8}} - Class - ShapedGraphic - ID - 34976 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 224}, {8, 24}} - Class - ShapedGraphic - ID - 34977 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 248}, {8, 8}} - Class - ShapedGraphic - ID - 34978 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 216}, {8, 8}} - Class - ShapedGraphic - ID - 34979 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34970 - Layer - 0 - - - Bounds - {{64, 176}, {192, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34969 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Settings} - VerticalPad - 0 - - - - Bounds - {{64, 136}, {192, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34968 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 News} - VerticalPad - 0 - - - - Class - Group - Graphics - - - Bounds - {{56, 208}, {208, 8}} - Class - ShapedGraphic - ID - 34959 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 176}, {208, 8}} - Class - ShapedGraphic - ID - 34960 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{56, 184}, {208, 24}} - Class - ShapedGraphic - ID - 34961 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 184}, {8, 24}} - Class - ShapedGraphic - ID - 34962 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 208}, {8, 8}} - Class - ShapedGraphic - ID - 34963 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 176}, {8, 8}} - Class - ShapedGraphic - ID - 34964 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 184}, {8, 24}} - Class - ShapedGraphic - ID - 34965 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 208}, {8, 8}} - Class - ShapedGraphic - ID - 34966 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 176}, {8, 8}} - Class - ShapedGraphic - ID - 34967 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34958 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{56, 168}, {208, 8}} - Class - ShapedGraphic - ID - 34949 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 136}, {208, 8}} - Class - ShapedGraphic - ID - 34950 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{56, 144}, {208, 24}} - Class - ShapedGraphic - ID - 34951 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 144}, {8, 24}} - Class - ShapedGraphic - ID - 34952 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 168}, {8, 8}} - Class - ShapedGraphic - ID - 34953 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{48, 136}, {8, 8}} - Class - ShapedGraphic - ID - 34954 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 144}, {8, 24}} - Class - ShapedGraphic - ID - 34955 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 168}, {8, 8}} - Class - ShapedGraphic - ID - 34956 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{264, 136}, {8, 8}} - Class - ShapedGraphic - ID - 34957 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34948 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 82}, {24, 4}} - Class - ShapedGraphic - ID - 34921 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 74}, {24, 4}} - Class - ShapedGraphic - ID - 34922 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 66}, {24, 4}} - Class - ShapedGraphic - ID - 34923 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34920 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 88}, {24, 8}} - Class - ShapedGraphic - ID - 34911 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 56}, {24, 8}} - Class - ShapedGraphic - ID - 34912 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 64}, {24, 24}} - Class - ShapedGraphic - ID - 34913 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34914 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34915 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34916 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34917 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34918 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34919 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34910 - Layer - 0 - - - Bounds - {{0, 0}, {320, 480}} - Class - ShapedGraphic - ID - 34909 - Layer - 1 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.8 - b - 0.999991 - g - 0.999974 - r - 1 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 0}, {320, 480}} - Class - ShapedGraphic - ID - 35082 - ImageID - 96 - Layer - 2 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - GridInfo - - GridSpacing - 8 - ShowsGrid - YES - SnapsToGrid - YES - - HPages - 1 - KeepToScale - - Layers - - - Lock - NO - Name - menu - Print - YES - View - YES - - - Lock - YES - Name - screen - Print - YES - View - YES - - - Lock - YES - Name - content - Print - YES - View - YES - - - LayoutInfo - - Animate - NO - circoMinDist - 18 - circoSeparation - 0.0 - layoutEngine - dot - neatoSeparation - 0.0 - twopiSeparation - 0.0 - - Orientation - 2 - PrintOnePage - - RowAlign - 1 - RowSpacing - 36 - SheetTitle - Option Menu - UniqueID - 5 - VPages - 1 - - - ActiveLayerIndex - 0 - AutoAdjust - - BackgroundGraphic - - Bounds - {{0, 0}, {320, 1472}} - Class - SolidGraphic - FontInfo - - Font - Helvetica-Bold - Size - 14 - - ID - 2 - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - BaseZoom - 0 - CanvasOrigin - {0, 0} - CanvasSize - {320, 1472} - ColumnAlign - 1 - ColumnSpacing - 36 - DisplayScale - 1 pt = 1 px - GraphicsList - - - Bounds - {{296, 464}, {16, 16}} - Class - ShapedGraphic - ID - 35101 - ImageID - 54 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.141442 - g - 0.070694 - r - 0.986343 - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{296, 120}, {16, 16}} - Class - ShapedGraphic - ID - 34994 - ImageID - 54 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.141442 - g - 0.070694 - r - 0.986343 - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 1096}, {320, 100}} - Class - ShapedGraphic - ID - 35099 - ImageID - 95 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 984}, {288, 80}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 35098 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs28 \cf0 For a long while now, Galacticraft has been the most requested mod, and it's finally here! Enjoy!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{8, 976}, {304, 96}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35097 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 952}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35096 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 2015-11-10} - VerticalPad - 0 - - - - Bounds - {{0, 680}, {320, 100}} - Class - ShapedGraphic - ID - 35092 - ImageID - 94 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 832}, {288, 88}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 35091 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs28 \cf0 One more small one over the weekend... Advanced Solar Panels has been added to crafting guide!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{8, 824}, {304, 104}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35090 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 800}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35089 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 2015-11-14} - VerticalPad - 0 - - - - Bounds - {{16, 584}, {288, 64}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 35088 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs28 \cf0 It's a small one, but also highly requested... Here's ComputerCraft!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{8, 576}, {304, 80}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35087 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 552}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35086 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 2015-11-16} - VerticalPad - 0 - - - - Bounds - {{16, 496}, {288, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 35085 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs28 \cf0 And today, it's Extra Cells!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{8, 488}, {304, 40}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35084 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 464}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35083 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 2015-11-17} - VerticalPad - 0 - - - - Bounds - {{0, 344}, {320, 100}} - Class - ShapedGraphic - ID - 35082 - ImageID - 93 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 152}, {288, 160}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 35025 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs28 \cf0 I'm super excited to announce that I've added full multi-block support for Crafting Guide! For example, check out a 5-Core Reactor from Big Reactors, or the 5x5x5 Steel Tank from Railcraft. I'm really pleased with how it turned out!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{8, 144}, {304, 176}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35039 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 120}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34202 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 2015-11-25} - VerticalPad - 0 - - - - Bounds - {{152, 56}, {96, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35036 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Search} - VerticalPad - 0 - - - - Bounds - {{144, 88}, {112, 8}} - Class - ShapedGraphic - ID - 35035 - ImageID - 18 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{144, 56}, {112, 8}} - Class - ShapedGraphic - ID - 35034 - ImageID - 17 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{144, 64}, {112, 24}} - Class - ShapedGraphic - ID - 35033 - ImageID - 16 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 64}, {8, 24}} - Class - ShapedGraphic - ID - 35032 - ImageID - 13 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 88}, {8, 8}} - Class - ShapedGraphic - ID - 35031 - ImageID - 12 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 56}, {8, 8}} - Class - ShapedGraphic - ID - 35030 - ImageID - 11 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 64}, {8, 24}} - Class - ShapedGraphic - ID - 35029 - ImageID - 10 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 88}, {8, 8}} - Class - ShapedGraphic - ID - 35028 - ImageID - 9 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 56}, {8, 8}} - Class - ShapedGraphic - ID - 35027 - ImageID - 8 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{184, 1385}, {79, 30}} - Class - ShapedGraphic - ID - 34678 - ImageID - 44 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{61, 1387}, {92, 26}} - Class - ShapedGraphic - ID - 34676 - ImageID - 43 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 1256}, {304, 104}} - Class - ShapedGraphic - FontInfo - - Color - - b - 0.999991 - g - 0.999974 - r - 1 - - Font - InputMono-Black - Size - 14 - - ID - 34675 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf1 Crafting guide is a free, open-source project by Andrew Miner. It is the result of hundreds of hours of work. Contributions are gratefully appreciated!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{0, 1440}, {320, 32}} - Class - ShapedGraphic - ID - 34674 - ImageID - 42 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{0, 1248}, {320, 224}} - Class - ShapedGraphic - ID - 34673 - Layer - 0 - Link - - url - https://github.com/andrewminer/crafting-guide/fork - - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.0313725 - g - 0.0862745 - r - 0.180392 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 1216}, {320, 32}} - Class - ShapedGraphic - ID - 34672 - ImageID - 41 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Class - Group - Graphics - - - Bounds - {{280, 82}, {24, 4}} - Class - ShapedGraphic - ID - 34225 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 74}, {24, 4}} - Class - ShapedGraphic - ID - 34226 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 66}, {24, 4}} - Class - ShapedGraphic - ID - 34227 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34224 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 88}, {24, 8}} - Class - ShapedGraphic - ID - 34229 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 56}, {24, 8}} - Class - ShapedGraphic - ID - 34230 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 64}, {24, 24}} - Class - ShapedGraphic - ID - 34231 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34232 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34233 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34234 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34235 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34236 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34237 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34228 - Layer - 0 - - - Bounds - {{24, 56}, {96, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34164 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Craft} - VerticalPad - 0 - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 34191 - Layer - 0 - Points - - {0, 48} - {320, 48} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{16, 88}, {112, 8}} - Class - ShapedGraphic - ID - 34190 - ImageID - 18 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 56}, {112, 8}} - Class - ShapedGraphic - ID - 34188 - ImageID - 17 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 64}, {112, 24}} - Class - ShapedGraphic - ID - 34186 - ImageID - 16 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34183 - ImageID - 13 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34182 - ImageID - 12 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34181 - ImageID - 11 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34180 - ImageID - 10 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34179 - ImageID - 9 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34178 - ImageID - 8 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 8}, {272, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 30 - - ID - 34161 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs60 \cf1 Crafting Guide} - VerticalPad - 0 - - - - Bounds - {{8, 8}, {32, 32}} - Class - ShapedGraphic - ID - 34160 - ImageID - 31 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 0}, {320, 48}} - Class - ShapedGraphic - ID - 34162 - ImageID - 4 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{0, 0}, {320, 1472}} - Class - ShapedGraphic - ID - 34901 - ImageID - 33 - Layer - 1 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - GridInfo - - GridSpacing - 8 - ShowsGrid - YES - SnapsToGrid - YES - - HPages - 1 - KeepToScale - - Layers - - - Lock - NO - Name - content - Print - YES - View - YES - - - Lock - YES - Name - background - Print - YES - View - YES - - - LayoutInfo - - Animate - NO - circoMinDist - 18 - circoSeparation - 0.0 - layoutEngine - dot - neatoSeparation - 0.0 - twopiSeparation - 0.0 - - Orientation - 2 - PrintOnePage - - RowAlign - 1 - RowSpacing - 36 - SheetTitle - News - UniqueID - 9 - VPages - 3 - - - ActiveLayerIndex - 0 - AutoAdjust - - BackgroundGraphic - - Bounds - {{0, 0}, {320, 2000}} - Class - SolidGraphic - FontInfo - - Font - Helvetica-Bold - Size - 14 - - ID - 2 - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - BaseZoom - 0 - CanvasOrigin - {0, 0} - CanvasSize - {320, 2000} - ColumnAlign - 1 - ColumnSpacing - 36 - DisplayScale - 1 pt = 1 px - GraphicsList - - - Bounds - {{0, 1312}, {320, 100}} - Class - ShapedGraphic - ID - 35026 - ImageID - 68 - Layer - 0 - Shape - Rectangle - Style - - fill - - Color - - b - 0.6 - g - 0.6 - r - 0.6 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 512}, {288, 80}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 35025 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs28 \cf0 A technical mod which adds power generation, mining, building and item/fluid/power transport systems} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{16, 472}, {288, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Black - Size - 20 - - ID - 35024 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs40 \cf0 BuildCraft} - VerticalPad - 0 - - TextPlacement - 0 - Wrap - NO - - - Bounds - {{16, 312}, {288, 160}} - Class - ShapedGraphic - ID - 35023 - ImageID - 61 - Layer - 0 - ManualSizeImage - YES - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 0 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 304}, {304, 296}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35022 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{0, 624}, {320, 100}} - Class - ShapedGraphic - ID - 35021 - ImageID - 67 - Layer - 0 - Shape - Rectangle - Style - - fill - - Color - - b - 0.6 - g - 0.6 - r - 0.6 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Class - Group - Graphics - - - Bounds - {{56, 160}, {264, 55.017543859649123}} - Class - ShapedGraphic - FontInfo - - Color - - b - 0.753828 - g - 0.753798 - r - 0.753849 - - Font - InputMono-Black - Size - 25 - - ID - 35063 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 12 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red192\green192\blue192;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs50 \cf2 search...} - - - - Bounds - {{8, 167.85964912280701}, {24, 23.578947368421051}} - Class - ShapedGraphic - ID - 35064 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Circle - Style - - shadow - - Draws - NO - - stroke - - Width - 3 - - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 35065 - Points - - {24, 183.57894736842107} - {44, 203.2280701754386} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - Width - 6 - - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 35066 - Points - - {0, 215.01754385964912} - {320, 215.01754385964912} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 35067 - Points - - {0, 160.00000000000003} - {320, 160.00000000000003} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{0, 160}, {320, 55.017543859649123}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 25 - - ID - 35068 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 12 - - - - ID - 35062 - Layer - 0 - - - Bounds - {{8, 284}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34202 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 OR CLICK a MOD...} - VerticalPad - 0 - - - - Bounds - {{16, 1640}, {288, 80}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 35008 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs28 \cf0 An expandable suit of powered armor while nearly infinite expansions, options, and customizations.} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{16, 1600}, {288, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Black - Size - 20 - - ID - 35007 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs40 \cf0 Modular Powersuits} - VerticalPad - 0 - - TextPlacement - 0 - Wrap - NO - - - Bounds - {{16, 1440}, {288, 160}} - Class - ShapedGraphic - ID - 35006 - ImageID - 60 - Layer - 0 - ManualSizeImage - YES - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 0 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 1432}, {304, 296}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35005 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{16, 1200}, {288, 80}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 35003 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs28 \cf0 A tech mod adding multiple tiers of ore processing and power, a breadth of tools and armor, and robots!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{16, 1160}, {288, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Black - Size - 20 - - ID - 35002 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs40 \cf0 Mekanism} - VerticalPad - 0 - - TextPlacement - 0 - Wrap - NO - - - Bounds - {{16, 1000}, {288, 160}} - Class - ShapedGraphic - ID - 35001 - ImageID - 59 - Layer - 0 - ManualSizeImage - YES - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 0 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 992}, {304, 296}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35000 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{16, 952}, {288, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 34997 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs28 \cf0 The basic game by itself} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{16, 912}, {288, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Black - Size - 20 - - ID - 34995 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\b\fs40 \cf0 Minecraft} - VerticalPad - 0 - - TextPlacement - 0 - Wrap - NO - - - Bounds - {{16, 752}, {288, 160}} - Class - ShapedGraphic - ID - 34994 - ImageID - 58 - Layer - 0 - ManualSizeImage - YES - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 0 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 744}, {304, 240}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 34205 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Class - Group - Graphics - - - Bounds - {{280, 82}, {24, 4}} - Class - ShapedGraphic - ID - 35030 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 74}, {24, 4}} - Class - ShapedGraphic - ID - 35031 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 66}, {24, 4}} - Class - ShapedGraphic - ID - 35032 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 35029 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 88}, {24, 8}} - Class - ShapedGraphic - ID - 35034 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 56}, {24, 8}} - Class - ShapedGraphic - ID - 35035 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 64}, {24, 24}} - Class - ShapedGraphic - ID - 35036 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 64}, {8, 24}} - Class - ShapedGraphic - ID - 35037 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 88}, {8, 8}} - Class - ShapedGraphic - ID - 35038 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 56}, {8, 8}} - Class - ShapedGraphic - ID - 35039 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 64}, {8, 24}} - Class - ShapedGraphic - ID - 35040 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 88}, {8, 8}} - Class - ShapedGraphic - ID - 35041 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 56}, {8, 8}} - Class - ShapedGraphic - ID - 35042 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 35033 - Layer - 0 - - - Bounds - {{184, 1913}, {79, 30}} - Class - ShapedGraphic - ID - 34678 - ImageID - 44 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{61, 1915}, {92, 26}} - Class - ShapedGraphic - ID - 34676 - ImageID - 43 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 1784}, {304, 104}} - Class - ShapedGraphic - FontInfo - - Color - - b - 0.999991 - g - 0.999974 - r - 1 - - Font - InputMono-Black - Size - 14 - - ID - 34675 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf1 Crafting guide is a free, open-source project by Andrew Miner. It is the result of hundreds of hours of work. Contributions are gratefully appreciated!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{0, 1968}, {320, 32}} - Class - ShapedGraphic - ID - 34674 - ImageID - 42 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{0, 1776}, {320, 224}} - Class - ShapedGraphic - ID - 34673 - Layer - 0 - Link - - url - https://github.com/andrewminer/crafting-guide/fork - - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.0313725 - g - 0.0862745 - r - 0.180392 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 1744}, {320, 32}} - Class - ShapedGraphic - ID - 34672 - ImageID - 41 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Class - Group - Graphics - - - Bounds - {{152, 56}, {96, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35044 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Search} - VerticalPad - 0 - - - - Bounds - {{144, 64}, {112, 24}} - Class - ShapedGraphic - ID - 35045 - ImageID - 28 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{144, 88}, {112, 8}} - Class - ShapedGraphic - ID - 35046 - ImageID - 27 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{144, 56}, {112, 8}} - Class - ShapedGraphic - ID - 35047 - ImageID - 26 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 64}, {8, 24}} - Class - ShapedGraphic - ID - 35048 - ImageID - 25 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 88}, {8, 8}} - Class - ShapedGraphic - ID - 35049 - ImageID - 24 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 56}, {8, 8}} - Class - ShapedGraphic - ID - 35050 - ImageID - 23 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 64}, {8, 24}} - Class - ShapedGraphic - ID - 35051 - ImageID - 22 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 88}, {8, 8}} - Class - ShapedGraphic - ID - 35052 - ImageID - 21 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 56}, {8, 8}} - Class - ShapedGraphic - ID - 35053 - ImageID - 20 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 35043 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{24, 56}, {96, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35055 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Craft} - VerticalPad - 0 - - - - Bounds - {{16, 88}, {112, 8}} - Class - ShapedGraphic - ID - 35056 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 56}, {112, 8}} - Class - ShapedGraphic - ID - 35057 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 64}, {112, 24}} - Class - ShapedGraphic - ID - 35058 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 64}, {8, 24}} - Class - ShapedGraphic - ID - 35059 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 88}, {8, 8}} - Class - ShapedGraphic - ID - 35060 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 56}, {8, 8}} - Class - ShapedGraphic - ID - 35061 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 35054 - Layer - 0 - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 34191 - Layer - 0 - Points - - {0, 48} - {320, 48} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{128, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34183 - ImageID - 13 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34182 - ImageID - 12 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34181 - ImageID - 11 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 8}, {272, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 30 - - ID - 34161 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs60 \cf1 Crafting Guide} - VerticalPad - 0 - - - - Bounds - {{8, 8}, {32, 32}} - Class - ShapedGraphic - ID - 34160 - ImageID - 31 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 0}, {320, 48}} - Class - ShapedGraphic - ID - 34162 - ImageID - 4 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{0, 0}, {320, 2000}} - Class - ShapedGraphic - ID - 34901 - ImageID - 33 - Layer - 1 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - GridInfo - - GridInFront - YES - GridSpacing - 8 - ShowsGrid - YES - SnapsToGrid - YES - - HPages - 1 - KeepToScale - - Layers - - - Lock - NO - Name - content - Print - YES - View - YES - - - Lock - YES - Name - background - Print - YES - View - YES - - - LayoutInfo - - Animate - NO - circoMinDist - 18 - circoSeparation - 0.0 - layoutEngine - dot - neatoSeparation - 0.0 - twopiSeparation - 0.0 - - Orientation - 2 - PrintOnePage - - RowAlign - 1 - RowSpacing - 36 - SheetTitle - Search - UniqueID - 7 - VPages - 3 - - - ActiveLayerIndex - 0 - AutoAdjust - - BackgroundGraphic - - Bounds - {{0, 0}, {320, 1744}} - Class - SolidGraphic - FontInfo - - Font - Helvetica-Bold - Size - 14 - - ID - 2 - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - BaseZoom - 0 - CanvasOrigin - {0, 0} - CanvasSize - {320, 1744} - ColumnAlign - 1 - ColumnSpacing - 36 - DisplayScale - 1 pt = 1 px - GraphicsList - - - Bounds - {{0, 1368}, {320, 100}} - Class - ShapedGraphic - ID - 35080 - ImageID - 86 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 1304}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35077 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Stirling Engine} - VerticalPad - 0 - - - - Bounds - {{16, 1304}, {32, 32}} - Class - ShapedGraphic - ID - 35076 - ImageID - 85 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 1264}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35075 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Redstone Engine} - VerticalPad - 0 - - - - Bounds - {{16, 1264}, {32, 32}} - Class - ShapedGraphic - ID - 35074 - ImageID - 84 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 1224}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35073 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Combustion Engine} - VerticalPad - 0 - - - - Bounds - {{16, 1224}, {32, 32}} - Class - ShapedGraphic - ID - 35072 - ImageID - 83 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 1184}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35071 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Charging Table} - VerticalPad - 0 - - - - Bounds - {{16, 1184}, {32, 32}} - Class - ShapedGraphic - ID - 35070 - ImageID - 82 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 1176}, {304, 168}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35069 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 1152}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35068 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 Energy Production} - VerticalPad - 0 - - - - Bounds - {{0, 776}, {320, 100}} - Class - ShapedGraphic - ID - 35067 - ImageID - 81 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 1088}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35065 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Pulsating Chipset} - VerticalPad - 0 - - - - Bounds - {{16, 1088}, {32, 32}} - Class - ShapedGraphic - ID - 35064 - ImageID - 79 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 1048}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35063 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Iron Chipset} - VerticalPad - 0 - - - - Bounds - {{16, 1048}, {32, 32}} - Class - ShapedGraphic - ID - 35062 - ImageID - 78 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 1008}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35061 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Golden Chipset} - VerticalPad - 0 - - - - Bounds - {{16, 1008}, {32, 32}} - Class - ShapedGraphic - ID - 35060 - ImageID - 77 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 968}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35059 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Emerald Chipset} - VerticalPad - 0 - - - - Bounds - {{16, 968}, {32, 32}} - Class - ShapedGraphic - ID - 35058 - ImageID - 76 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 928}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35057 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Diamond Chipset} - VerticalPad - 0 - - - - Bounds - {{16, 928}, {32, 32}} - Class - ShapedGraphic - ID - 35056 - ImageID - 75 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 920}, {304, 208}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35055 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 896}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35054 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 Chipsets} - VerticalPad - 0 - - - - Bounds - {{56, 712}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35053 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Blueprint Library} - VerticalPad - 0 - - - - Bounds - {{16, 712}, {32, 32}} - Class - ShapedGraphic - ID - 35052 - ImageID - 74 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 672}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35051 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Blueprint} - VerticalPad - 0 - - - - Bounds - {{16, 672}, {32, 32}} - Class - ShapedGraphic - ID - 35050 - ImageID - 73 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 632}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35049 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Auto Workbench} - VerticalPad - 0 - - - - Bounds - {{16, 632}, {32, 32}} - Class - ShapedGraphic - ID - 35048 - ImageID - 72 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 592}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35047 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Architect Table} - VerticalPad - 0 - - - - Bounds - {{16, 592}, {32, 32}} - Class - ShapedGraphic - ID - 35046 - ImageID - 71 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{56, 552}, {248, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35045 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Advanced Crafting Table} - VerticalPad - 0 - - - - Bounds - {{16, 552}, {32, 32}} - Class - ShapedGraphic - ID - 35044 - ImageID - 70 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 544}, {304, 208}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35043 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 520}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35042 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 Building Machines} - VerticalPad - 0 - - - - Bounds - {{104, 408}, {200, 80}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Color - - b - 0.69763 - g - 0 - r - 0.0533003 - - Font - InputMono-Black - Size - 14 - - ID - 35041 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;\red14\green0\blue178;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf2 \ul \ulc2 Gates, Wires, and Chips} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{16, 408}, {80, 80}} - Class - ShapedGraphic - ID - 35040 - ImageID - 69 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 400}, {304, 96}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35039 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{8, 376}, {304, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34202 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs40 \cf0 Tutorials} - VerticalPad - 0 - - - - Bounds - {{16, 320}, {176, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 35038 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\fs28 \cf0 by SpaceToad} - VerticalPad - 0 - - - - Bounds - {{192, 320}, {112, 24}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Regular - Size - 14 - - ID - 35037 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 2 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Regular;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qr - -\f0\fs28 \cf0 v6.4.6} - VerticalPad - 0 - - - - Bounds - {{152, 56}, {96, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 35036 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Search} - VerticalPad - 0 - - - - Bounds - {{144, 88}, {112, 8}} - Class - ShapedGraphic - ID - 35035 - ImageID - 18 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{144, 56}, {112, 8}} - Class - ShapedGraphic - ID - 35034 - ImageID - 17 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{144, 64}, {112, 24}} - Class - ShapedGraphic - ID - 35033 - ImageID - 16 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 64}, {8, 24}} - Class - ShapedGraphic - ID - 35032 - ImageID - 13 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 88}, {8, 8}} - Class - ShapedGraphic - ID - 35031 - ImageID - 12 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{256, 56}, {8, 8}} - Class - ShapedGraphic - ID - 35030 - ImageID - 11 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 64}, {8, 24}} - Class - ShapedGraphic - ID - 35029 - ImageID - 10 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 88}, {8, 8}} - Class - ShapedGraphic - ID - 35028 - ImageID - 9 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{136, 56}, {8, 8}} - Class - ShapedGraphic - ID - 35027 - ImageID - 8 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 288}, {288, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - InputMono-Black - Size - 20 - - ID - 35024 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs40 \cf0 BuildCraft} - VerticalPad - 0 - - TextPlacement - 0 - Wrap - NO - - - Bounds - {{16, 120}, {288, 160}} - Class - ShapedGraphic - ID - 35023 - ImageID - 61 - Layer - 0 - ManualSizeImage - YES - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 0 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 112}, {304, 240}} - Class - ShapedGraphic - FontInfo - - Font - InputMono-Black - Size - 14 - - ID - 35022 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - a - 0.7 - b - 1 - g - 1 - r - 1 - - - shadow - - Beneath - YES - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - - - - Bounds - {{292, 60}, {16, 16}} - Class - ShapedGraphic - ID - 34993 - ImageID - 54 - Layer - 0 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.141442 - g - 0.070694 - r - 0.986343 - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{184, 1657}, {79, 30}} - Class - ShapedGraphic - ID - 34678 - ImageID - 44 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{61, 1659}, {92, 26}} - Class - ShapedGraphic - ID - 34676 - ImageID - 43 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{8, 1528}, {304, 104}} - Class - ShapedGraphic - FontInfo - - Color - - b - 0.999991 - g - 0.999974 - r - 1 - - Font - InputMono-Black - Size - 14 - - ID - 34675 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Align - 0 - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 InputMono-Black;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural - -\f0\b\fs28 \cf1 Crafting guide is a free, open-source project by Andrew Miner. It is the result of hundreds of hours of work. Contributions are gratefully appreciated!} - VerticalPad - 0 - - TextPlacement - 0 - - - Bounds - {{0, 1712}, {320, 32}} - Class - ShapedGraphic - ID - 34674 - ImageID - 42 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{0, 1520}, {320, 224}} - Class - ShapedGraphic - ID - 34673 - Layer - 0 - Link - - url - https://github.com/andrewminer/crafting-guide/fork - - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - fill - - Color - - b - 0.0313725 - g - 0.0862745 - r - 0.180392 - - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 1488}, {320, 32}} - Class - ShapedGraphic - ID - 34672 - ImageID - 41 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Class - Group - Graphics - - - Bounds - {{280, 82}, {24, 4}} - Class - ShapedGraphic - ID - 34225 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 74}, {24, 4}} - Class - ShapedGraphic - ID - 34226 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 66}, {24, 4}} - Class - ShapedGraphic - ID - 34227 - Magnets - - {-0.59628479784302701, -1.1925696134567261} - {1.9868215517249155e-08, -1.3333333730697632} - {0.59628487781105122, -1.1925696134567261} - {1.1925696134567261, -0.59628480672836304} - {1.3333333730697632, 1.5894572413799324e-07} - {1.1925696134567261, 0.59628473564567486} - {0.59628465308492196, 1.1925697326660156} - {0, 1.3333333730697632} - {-0.5962849488937394, 1.1925696134567261} - {-1.1925697326660156, 0.5962844398368361} - {-1.3333333730697632, -6.3578289655197295e-07} - {-1.1925696134567261, -0.59628480672836304} - - Shape - Rectangle - Style - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - ID - 34224 - Layer - 0 - - - Class - Group - Graphics - - - Bounds - {{280, 88}, {24, 8}} - Class - ShapedGraphic - ID - 34229 - ImageID - 18 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{280, 56}, {24, 8}} - Class - ShapedGraphic - ID - 34230 - ImageID - 17 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{280, 64}, {24, 24}} - Class - ShapedGraphic - ID - 34231 - ImageID - 16 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34232 - ImageID - 10 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34233 - ImageID - 9 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{272, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34234 - ImageID - 8 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34235 - ImageID - 13 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34236 - ImageID - 12 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{304, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34237 - ImageID - 11 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - ID - 34228 - Layer - 0 - - - Bounds - {{24, 56}, {96, 40}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 20 - - ID - 34164 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs40 \cf1 Craft} - VerticalPad - 0 - - - - AllowConnections - NO - AllowLabelDrop - - AllowToConnect - - Class - LineGraphic - ID - 34191 - Layer - 0 - Points - - {0, 48} - {320, 48} - - Style - - stroke - - HeadArrow - 0 - Legacy - - TailArrow - 0 - - - - - Bounds - {{16, 88}, {112, 8}} - Class - ShapedGraphic - ID - 34190 - ImageID - 18 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{16, 56}, {112, 8}} - Class - ShapedGraphic - ID - 34188 - ImageID - 17 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{16, 64}, {112, 24}} - Class - ShapedGraphic - ID - 34186 - ImageID - 16 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34183 - ImageID - 13 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34182 - ImageID - 12 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{128, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34181 - ImageID - 11 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 64}, {8, 24}} - Class - ShapedGraphic - ID - 34180 - ImageID - 10 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 88}, {8, 8}} - Class - ShapedGraphic - ID - 34179 - ImageID - 9 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{8, 56}, {8, 8}} - Class - ShapedGraphic - ID - 34178 - ImageID - 8 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{40, 8}, {272, 32}} - Class - ShapedGraphic - FitText - Clip - Flow - Clip - FontInfo - - Font - Silkscreen - Size - 30 - - ID - 34161 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - Text - - Pad - 0 - Text - {\rtf1\ansi\ansicpg1252\cocoartf1348\cocoasubrtf170 -\cocoascreenfonts1{\fonttbl\f0\fnil\fcharset0 Silkscreen;} -{\colortbl;\red255\green255\blue255;} -\pard\tx560\tx1120\tx1680\tx2240\tx2800\tx3360\tx3920\tx4480\tx5040\tx5600\tx6160\tx6720\pardirnatural\qc - -\f0\fs60 \cf1 Crafting Guide} - VerticalPad - 0 - - - - Bounds - {{8, 8}, {32, 32}} - Class - ShapedGraphic - ID - 34160 - ImageID - 31 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - shadow - - Draws - NO - - stroke - - Draws - NO - - - - - Bounds - {{0, 0}, {320, 48}} - Class - ShapedGraphic - ID - 34162 - ImageID - 4 - Layer - 0 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - Bounds - {{0, 0}, {320, 1744}} - Class - ShapedGraphic - ID - 34901 - ImageID - 33 - Layer - 1 - Shape - Rectangle - Style - - fill - - Draws - NO - - image fill - - ImageSizing - 2 - - shadow - - Draws - NO - - stroke - - Draws - NO - - - TiledImage - YES - - - GridInfo - - GridSpacing - 8 - ShowsGrid - YES - SnapsToGrid - YES - - HPages - 1 - KeepToScale - - Layers - - - Lock - NO - Name - content - Print - YES - View - YES - - - Lock - YES - Name - background - Print - YES - View - YES - - - LayoutInfo - - Animate - NO - circoMinDist - 18 - circoSeparation - 0.0 - layoutEngine - dot - neatoSeparation - 0.0 - twopiSeparation - 0.0 - - Orientation - 2 - PrintOnePage - - RowAlign - 1 - RowSpacing - 36 - SheetTitle - Mod Detail - UniqueID - 8 - VPages - 3 - - - SmartAlignmentGuidesActive - YES - SmartDistanceGuidesActive - YES - UseEntirePage - - WindowInfo - - CurrentSheet - 3 - ExpandedCanvases - - Frame - {{248, 0}, {1259, 1417}} - ListView - - OutlineWidth - 142 - RightSidebar - - ShowRuler - - Sidebar - - SidebarWidth - 158 - VisibleRegion - {{-383, -397}, {1086, 1275}} - Zoom - 1 - ZoomValues - - - Craft (with steps) - 1 - 2.1500000953674316 - - - Item Chooser - 2 - 1 - - - Quantity Chooser - 1 - 2 - - - Option Menu - 1 - 2 - - - Craft (empty) - 2 - 1 - - - Search - 2 - 1 - - - Mod Detail - 2 - 1 - - - News - 1 - 2 - - - - - diff --git a/design/v3/mobile-website.graffle/image10.tiff b/design/v3/mobile-website.graffle/image10.tiff deleted file mode 100644 index 91df13937..000000000 Binary files a/design/v3/mobile-website.graffle/image10.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image11.tiff b/design/v3/mobile-website.graffle/image11.tiff deleted file mode 100644 index 922d63e2b..000000000 Binary files a/design/v3/mobile-website.graffle/image11.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image12.tiff b/design/v3/mobile-website.graffle/image12.tiff deleted file mode 100644 index 466e97f26..000000000 Binary files a/design/v3/mobile-website.graffle/image12.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image13.tiff b/design/v3/mobile-website.graffle/image13.tiff deleted file mode 100644 index 2da21cb79..000000000 Binary files a/design/v3/mobile-website.graffle/image13.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image16.tiff b/design/v3/mobile-website.graffle/image16.tiff deleted file mode 100644 index 287c646cb..000000000 Binary files a/design/v3/mobile-website.graffle/image16.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image17.tiff b/design/v3/mobile-website.graffle/image17.tiff deleted file mode 100644 index 7779aa767..000000000 Binary files a/design/v3/mobile-website.graffle/image17.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image18.tiff b/design/v3/mobile-website.graffle/image18.tiff deleted file mode 100644 index ebc8d6789..000000000 Binary files a/design/v3/mobile-website.graffle/image18.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image20.tiff b/design/v3/mobile-website.graffle/image20.tiff deleted file mode 100644 index 9be2172f2..000000000 Binary files a/design/v3/mobile-website.graffle/image20.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image21.tiff b/design/v3/mobile-website.graffle/image21.tiff deleted file mode 100644 index 8a1a9e1c7..000000000 Binary files a/design/v3/mobile-website.graffle/image21.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image22.tiff b/design/v3/mobile-website.graffle/image22.tiff deleted file mode 100644 index 2d2787c04..000000000 Binary files a/design/v3/mobile-website.graffle/image22.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image23.tiff b/design/v3/mobile-website.graffle/image23.tiff deleted file mode 100644 index 3b496d737..000000000 Binary files a/design/v3/mobile-website.graffle/image23.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image24.tiff b/design/v3/mobile-website.graffle/image24.tiff deleted file mode 100644 index 3f46f4291..000000000 Binary files a/design/v3/mobile-website.graffle/image24.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image25.tiff b/design/v3/mobile-website.graffle/image25.tiff deleted file mode 100644 index 12385779a..000000000 Binary files a/design/v3/mobile-website.graffle/image25.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image26.tiff b/design/v3/mobile-website.graffle/image26.tiff deleted file mode 100644 index 9b4a28f93..000000000 Binary files a/design/v3/mobile-website.graffle/image26.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image27.tiff b/design/v3/mobile-website.graffle/image27.tiff deleted file mode 100644 index c42779916..000000000 Binary files a/design/v3/mobile-website.graffle/image27.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image28.tiff b/design/v3/mobile-website.graffle/image28.tiff deleted file mode 100644 index 784f5e22b..000000000 Binary files a/design/v3/mobile-website.graffle/image28.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image31.tiff b/design/v3/mobile-website.graffle/image31.tiff deleted file mode 100644 index fa53023cb..000000000 Binary files a/design/v3/mobile-website.graffle/image31.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image33.tiff b/design/v3/mobile-website.graffle/image33.tiff deleted file mode 100644 index a7fc65ce2..000000000 Binary files a/design/v3/mobile-website.graffle/image33.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image35.png b/design/v3/mobile-website.graffle/image35.png deleted file mode 100644 index 276bacc51..000000000 Binary files a/design/v3/mobile-website.graffle/image35.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image36.png b/design/v3/mobile-website.graffle/image36.png deleted file mode 100644 index 61f1a4731..000000000 Binary files a/design/v3/mobile-website.graffle/image36.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image37.png b/design/v3/mobile-website.graffle/image37.png deleted file mode 100644 index a397393ab..000000000 Binary files a/design/v3/mobile-website.graffle/image37.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image38.png b/design/v3/mobile-website.graffle/image38.png deleted file mode 100644 index d13cd5471..000000000 Binary files a/design/v3/mobile-website.graffle/image38.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image39.png b/design/v3/mobile-website.graffle/image39.png deleted file mode 100644 index 8adfae2e0..000000000 Binary files a/design/v3/mobile-website.graffle/image39.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image4.png b/design/v3/mobile-website.graffle/image4.png deleted file mode 100644 index f810cdeb7..000000000 Binary files a/design/v3/mobile-website.graffle/image4.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image40.tiff b/design/v3/mobile-website.graffle/image40.tiff deleted file mode 100644 index 24cb5ad05..000000000 Binary files a/design/v3/mobile-website.graffle/image40.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image41.tiff b/design/v3/mobile-website.graffle/image41.tiff deleted file mode 100644 index 53f6b4643..000000000 Binary files a/design/v3/mobile-website.graffle/image41.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image42.tiff b/design/v3/mobile-website.graffle/image42.tiff deleted file mode 100644 index ab6c31820..000000000 Binary files a/design/v3/mobile-website.graffle/image42.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image43.tiff b/design/v3/mobile-website.graffle/image43.tiff deleted file mode 100644 index 38af6f3e3..000000000 Binary files a/design/v3/mobile-website.graffle/image43.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image44.tiff b/design/v3/mobile-website.graffle/image44.tiff deleted file mode 100644 index e5ab02a75..000000000 Binary files a/design/v3/mobile-website.graffle/image44.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image46.tiff b/design/v3/mobile-website.graffle/image46.tiff deleted file mode 100644 index 3cef1c0c4..000000000 Binary files a/design/v3/mobile-website.graffle/image46.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image48.png b/design/v3/mobile-website.graffle/image48.png deleted file mode 100644 index ea6f940be..000000000 Binary files a/design/v3/mobile-website.graffle/image48.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image49.png b/design/v3/mobile-website.graffle/image49.png deleted file mode 100644 index ee8964b2d..000000000 Binary files a/design/v3/mobile-website.graffle/image49.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image50.png b/design/v3/mobile-website.graffle/image50.png deleted file mode 100644 index 78819aeb4..000000000 Binary files a/design/v3/mobile-website.graffle/image50.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image51.png b/design/v3/mobile-website.graffle/image51.png deleted file mode 100644 index 0e8bc0f49..000000000 Binary files a/design/v3/mobile-website.graffle/image51.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image52.png b/design/v3/mobile-website.graffle/image52.png deleted file mode 100644 index 937d300a4..000000000 Binary files a/design/v3/mobile-website.graffle/image52.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image54.png b/design/v3/mobile-website.graffle/image54.png deleted file mode 100644 index e8d9cc447..000000000 Binary files a/design/v3/mobile-website.graffle/image54.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image58.png b/design/v3/mobile-website.graffle/image58.png deleted file mode 100644 index ac10dbd1e..000000000 Binary files a/design/v3/mobile-website.graffle/image58.png and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image59.tiff b/design/v3/mobile-website.graffle/image59.tiff deleted file mode 100644 index 85c048697..000000000 Binary files a/design/v3/mobile-website.graffle/image59.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image60.tiff b/design/v3/mobile-website.graffle/image60.tiff deleted file mode 100644 index 2a4417ef4..000000000 Binary files a/design/v3/mobile-website.graffle/image60.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image61.tiff b/design/v3/mobile-website.graffle/image61.tiff deleted file mode 100644 index 97e7eb931..000000000 Binary files a/design/v3/mobile-website.graffle/image61.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image62.tiff b/design/v3/mobile-website.graffle/image62.tiff deleted file mode 100644 index 4cfa7fe5a..000000000 Binary files a/design/v3/mobile-website.graffle/image62.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image64.tiff b/design/v3/mobile-website.graffle/image64.tiff deleted file mode 100644 index 1bc7a9eb9..000000000 Binary files a/design/v3/mobile-website.graffle/image64.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image65.tiff b/design/v3/mobile-website.graffle/image65.tiff deleted file mode 100644 index 1b5c61aec..000000000 Binary files a/design/v3/mobile-website.graffle/image65.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image67.tiff b/design/v3/mobile-website.graffle/image67.tiff deleted file mode 100644 index e099589b9..000000000 Binary files a/design/v3/mobile-website.graffle/image67.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image68.tiff b/design/v3/mobile-website.graffle/image68.tiff deleted file mode 100644 index faa8313c5..000000000 Binary files a/design/v3/mobile-website.graffle/image68.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image69.tiff b/design/v3/mobile-website.graffle/image69.tiff deleted file mode 100644 index 7e3d38f60..000000000 Binary files a/design/v3/mobile-website.graffle/image69.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image70.tiff b/design/v3/mobile-website.graffle/image70.tiff deleted file mode 100644 index 5f7c2473d..000000000 Binary files a/design/v3/mobile-website.graffle/image70.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image71.tiff b/design/v3/mobile-website.graffle/image71.tiff deleted file mode 100644 index 288144613..000000000 Binary files a/design/v3/mobile-website.graffle/image71.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image72.tiff b/design/v3/mobile-website.graffle/image72.tiff deleted file mode 100644 index 18c996385..000000000 Binary files a/design/v3/mobile-website.graffle/image72.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image73.tiff b/design/v3/mobile-website.graffle/image73.tiff deleted file mode 100644 index 51d4487d2..000000000 Binary files a/design/v3/mobile-website.graffle/image73.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image74.tiff b/design/v3/mobile-website.graffle/image74.tiff deleted file mode 100644 index b3854a979..000000000 Binary files a/design/v3/mobile-website.graffle/image74.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image75.tiff b/design/v3/mobile-website.graffle/image75.tiff deleted file mode 100644 index 18ce90e0d..000000000 Binary files a/design/v3/mobile-website.graffle/image75.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image76.tiff b/design/v3/mobile-website.graffle/image76.tiff deleted file mode 100644 index 5288892da..000000000 Binary files a/design/v3/mobile-website.graffle/image76.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image77.tiff b/design/v3/mobile-website.graffle/image77.tiff deleted file mode 100644 index 27e5ac6d8..000000000 Binary files a/design/v3/mobile-website.graffle/image77.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image78.tiff b/design/v3/mobile-website.graffle/image78.tiff deleted file mode 100644 index 50ad7a00f..000000000 Binary files a/design/v3/mobile-website.graffle/image78.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image79.tiff b/design/v3/mobile-website.graffle/image79.tiff deleted file mode 100644 index 1350a9db8..000000000 Binary files a/design/v3/mobile-website.graffle/image79.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image8.tiff b/design/v3/mobile-website.graffle/image8.tiff deleted file mode 100644 index 64636470c..000000000 Binary files a/design/v3/mobile-website.graffle/image8.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image81.tiff b/design/v3/mobile-website.graffle/image81.tiff deleted file mode 100644 index e981db68c..000000000 Binary files a/design/v3/mobile-website.graffle/image81.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image82.tiff b/design/v3/mobile-website.graffle/image82.tiff deleted file mode 100644 index de80dbd5f..000000000 Binary files a/design/v3/mobile-website.graffle/image82.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image83.tiff b/design/v3/mobile-website.graffle/image83.tiff deleted file mode 100644 index 3df9ae4df..000000000 Binary files a/design/v3/mobile-website.graffle/image83.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image84.tiff b/design/v3/mobile-website.graffle/image84.tiff deleted file mode 100644 index 8bed627f3..000000000 Binary files a/design/v3/mobile-website.graffle/image84.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image85.tiff b/design/v3/mobile-website.graffle/image85.tiff deleted file mode 100644 index b9b64b6e9..000000000 Binary files a/design/v3/mobile-website.graffle/image85.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image86.tiff b/design/v3/mobile-website.graffle/image86.tiff deleted file mode 100644 index 09649598d..000000000 Binary files a/design/v3/mobile-website.graffle/image86.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image9.tiff b/design/v3/mobile-website.graffle/image9.tiff deleted file mode 100644 index f0c296da3..000000000 Binary files a/design/v3/mobile-website.graffle/image9.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image91.tiff b/design/v3/mobile-website.graffle/image91.tiff deleted file mode 100644 index dea3a2e02..000000000 Binary files a/design/v3/mobile-website.graffle/image91.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image92.tiff b/design/v3/mobile-website.graffle/image92.tiff deleted file mode 100644 index cda558256..000000000 Binary files a/design/v3/mobile-website.graffle/image92.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image93.tiff b/design/v3/mobile-website.graffle/image93.tiff deleted file mode 100644 index 8fd662a95..000000000 Binary files a/design/v3/mobile-website.graffle/image93.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image94.tiff b/design/v3/mobile-website.graffle/image94.tiff deleted file mode 100644 index 57564add4..000000000 Binary files a/design/v3/mobile-website.graffle/image94.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image95.tiff b/design/v3/mobile-website.graffle/image95.tiff deleted file mode 100644 index 82ea2d23f..000000000 Binary files a/design/v3/mobile-website.graffle/image95.tiff and /dev/null differ diff --git a/design/v3/mobile-website.graffle/image96.tiff b/design/v3/mobile-website.graffle/image96.tiff deleted file mode 100644 index 6a2e0cef8..000000000 Binary files a/design/v3/mobile-website.graffle/image96.tiff and /dev/null differ diff --git a/marketing/forum-posts.txt b/marketing/forum-posts.txt deleted file mode 100644 index 4de58e645..000000000 --- a/marketing/forum-posts.txt +++ /dev/null @@ -1,114 +0,0 @@ -Title: - -MAJOR UPDATE! Crafting Guide—Ultimate step-by-step guide to make anything - -Body: - -Have you ever wanted to figure out how much of what materials you need to craft something? Ever notice that certain -recipes are pretty easy... until you account for all the machines you need? Ever wonder how much stuff you'll need to -make a [Quarry](http://crafting-guide.com/item/quarry) or an entire -[QuantumSuit](http://crafting-guide.com/quantumsuit_bodyarmor)? - -Crafting Guide will help. Choose what you want to make and how many of each, and it will automatically figure out: - -* How many of what resources do you need? -* What tools / machines do you need? -* How many of what resource do you need for the tools? -* What items do you need to craft in what order? - -I've just launched a brand-new version with support for vanilla, Buildcraft, and IndustrialCraft2 (classic) recipes. -It's all open-source, so anyone can help expand it to cover missing recipes, other mods, or add new features. Check out -the [GitHub project](https://github.com/andrewminer/crafting-guide) if you'd like to get involved! - -If you've seen it before, go look again. There's a whole new site now, which supports a lot more than the old one did: - -* All items have matching icons -* All recipes show the proper layout on the crafting grid -* You now get step-by-step instructions -* You can now make many different items at once (e.g., a whole NanoSuit) - -[crafting-guide.com](http://crafting-guide.com) - -######################################################################################################################## - -A few more updates to report! First, now your preferences for which mods are active and whether tools are included -will be remembered between visits. Second, I've finished adding support for Thermal Expansion 4. The crafting algorithm -doesn't yet taken into account the ore-doubling/tripling machinery, but all the recipes for the entire mod are present -and functional. I'll work on using the machines in a future update. Next up: IC2 Experimental! - -######################################################################################################################## - -I've just finished adding support for the latest version of Industrial Craft (2.2.663 on the experimental branch). I've -also updated the site to let you select the version you're using. - -######################################################################################################################## - -I just pushed up a big new feature! Now, each Mod has a dedicated page of its own which lists all the items available -in that mod. Clicking on an item will take you to the crafting guide for that item. It's super fast to switch back and -forth to explore the items in any given mod. This is the first of many steps for the new mod pages, so keep an eye out -for more to come! - -######################################################################################################################## - - -I've been working on a project to make it easier to deal with complex recipes, and I recently finished adding all the -core Minecraft recipes. The gist of the site is that you tell it what item(s) you want to make, and it will figure out -all the raw ingredients you need along with step-by-step instructions for any number of whatever items you like. For -example, [http://crafting-guide.com/crafting/16.potion_of_fire_resistance_8_00:16.potion_of_healing_ii here's how you -make] 16 potions of healing II and fire resistance (with extended duration). - -The maintainers of many of the mods I've added (e.g., BuildCraft / Applied Energistics) have found it useful to include -links to Crafting Guide in their official documentation, and I was hoping you would think it a good idea to add links -from this wiki to CraftingGuide as well. I'd be happy to do the work of adding the links myself, but I'd like to make -sure there are no objections first! - -Thanks! -~~~~ - -######################################################################################################################## - -Crafting Guide—the ultimate step-by-step guide for Minecraft—Now with item detail pages! - -I just pushed up another big update! This one adds detail pages for each item from each mod. These detail pages show: - -* the item's basic information (name, icon, ...) -* a link to the item's full crafting plan -* the list of all recipes for that item -* the list of all items it can be used to make -* the list of all similar items - -All of this gives you an extensive reference of related items and recipes. Check it out by seeing what you can do with -a [Diamond](http://crafting-guide.com/item/diamond)! - -######################################################################################################################## - -I just released another exciting update for Crafting Guide! This update adds a lot of small tweaks and adjustments to -the site's animations and some performance enhancements, but the big news is an enhanced crafting algorithm and -Railcraft support! - -The new crafting algorithm, instead of using the first available recipe for any given item, will now choose the recipe -which is most effecient at producing that item. In other words, if you have a Macerator, it will be smart enough to use -it. It is also smart about using machines like the Block Cutting Machine to make plates. And, as an extra bonus, it's -about twice as fast as the old algorithm. - -With Railcraft support not only comes the huge richness of that mod, but the first multi-block structures in Crafting -Guide. For example, check out how to make a [url=http://crafting-guide.com/crafting/blast_furnace]Blast Furnace[/url]! - -######################################################################################################################## - -Another big release for Crafting Guide! This time, I've been working on the navigation of the site itself. You'll now -see a small navigation bar at the top of each page which both tells you where you are as well as letting you jump to -another location. This make the whole item/mod-browsing part of the site much more visible, and simplifies the crafting -page a bit. There's even a real home page with a change log! - -######################################################################################################################## - -It's been a while, but I just posted some new stuff for Crafting Guide. First, a volunteer took on the rather daunting -task of adding Forestry support! It's all there in all its glorious plethora of species. Major kudos to Sheldon Griffin -for making it happen. - -Second, I've just finished the coding to majorly improve the item pages. Now, its possible to add a markdown description -of the item (including images) as well as videos for each item. Of course, actually filling in the content is a whole -different kettle of fish. The Buildcraft guys have generously given me permission to copy in their content, so I'm -going to be busy doing that for a while. However, you can see the finished product for the -[url=http://crafting-guide.com/browse/buildcraft/advanced_crafting_table/]Advanced Crafting Table[/url]. More to come! \ No newline at end of file diff --git a/package.json b/package.json index 158b07672..eef97b5e9 100644 --- a/package.json +++ b/package.json @@ -1,51 +1,49 @@ { "name": "crafting-guide", - "version": "1.15.1", - "description": "Source code for http://crafting-guide.com", + "version": "1.0.0", + "description": "A guide for building anything in Minecraft or its many mods", "main": "./dist/index.js", + "repository": "http://github.com/andrewminer/crafting-guide", "scripts": { + "build": "grunt build", "prepublish": "grunt prepublish", - "start": "./scripts/server", + "start": "grunt start", "test": "grunt test" }, - "repository": { - "type": "git", - "url": "https://github.com/andrewminer/crafting-guide.git" - }, "author": "Andrew Miner", - "bugs": { - "url": "https://github.com/andrewminer/crafting-guide/issues" - }, - "homepage": "https://github.com/andrewminer/crafting-guide", + "license": "none", "devDependencies": { "chai": "^1.10.0", - "coffee-script": "^1.9.1", + "coffee-script": "^1.9.3", "coffeeify": "^1.1.0", - "express": "^4.10.6", "grunt": "^0.4.5", - "grunt-browserify": "^3.2.1", "grunt-contrib-clean": "^0.6.0", - "grunt-contrib-coffee": "^0.13.0", - "grunt-contrib-copy": "^0.7.0", - "grunt-contrib-jade": "^0.13.0", - "grunt-contrib-sass": "^0.8.1", - "grunt-contrib-uglify": "^0.7.0", + "grunt-contrib-compress": "^0.14.0", + "grunt-contrib-copy": "^0.8.2", + "grunt-contrib-jade": "^0.15.0", + "grunt-contrib-sass": "^0.9.2", + "grunt-contrib-uglify": "^0.11.0", "grunt-contrib-watch": "^0.6.1", - "grunt-exorcise": "^1.0.1", "grunt-mocha-test": "^0.12.7", - "grunt-rename": "^0.1.4", - "grunt-rsync": "^0.6.2", - "mocha": "^2.2.1", + "grunt-sass-globbing": "^1.4.0", + "mocha": "^2.4.5", + "sass": "^0.5.0", "sinon": "^1.14.1", "sinon-chai": "^2.7.0" }, "dependencies": { - "backbone": "^1.1.2", - "crafting-guide-common": "^1.0.0", - "jade": "^1.8.2", - "jquery": "^2.1.3", - "marked": "^0.3.3", - "underscore": "^1.7.0", - "when": "^3.6.4" + "backbone": "^1.2.3", + "body-parser": "^1.13.3", + "client-sessions": "^0.7.0", + "cookie-parser": "^1.3.5", + "crafting-guide-common": "^1.5.1", + "express": "^4.13.3", + "express-session": "^1.11.3", + "jade": "^1.11.0", + "jquery": "^2.1.4", + "marked": "^0.3.5", + "underscore": "^1.8.3", + "underscore.inflections": "^0.2.1", + "when": "^3.7.3" } } diff --git a/scripts/all b/scripts/all deleted file mode 100755 index a642430ee..000000000 --- a/scripts/all +++ /dev/null @@ -1,27 +0,0 @@ -#!/bin/bash - -USAGE=< - - Executes a command for this project and each project related to this one. - Related projects must include this project's name as a prefix in their name - to be considered related. - -END - -COMMAND="$1" -[[ "$COMMAND" == "" ]] && echo $USAGE && exit 1 - -SRC_ROOT="/src" -BASE_NAME=$(basename $PWD) - -pushd $SRC_ROOT &>/dev/null - -for MODULE in $(ls | grep "$BASE_NAME"); do - cd "$SRC_ROOT/$MODULE" - if [[ -e './scripts/unpublished' ]]; then - ./scripts/unpublished - fi -done - -popd &>/dev/null diff --git a/scripts/deploy b/scripts/deploy index 5017e9cb8..0bf97cea0 100755 --- a/scripts/deploy +++ b/scripts/deploy @@ -1,51 +1,22 @@ #!/bin/bash -USAGE=< "$S3CMD_CFG" - cat $AWS_CONFIG_FILE | grep "aws_access_key_id" | sed "s/aws_access_key_id/access_key/" >> "$S3CMD_CFG" - cat $AWS_CONFIG_FILE | grep "aws_secret_access_key" | sed "s/aws_secret_access_key/secret_key/" >> "$S3CMD_CFG" -fi - -if grunt clean $BUILD_CMD; then - echo "Preparing to upload to S3..." - s3cmd sync -r -P --add-header="cache-control:max-age=1800" $SOURCE_DIR $TARGET_DIR - echo "S3 Upload Complete" -else - echo "ERROR: Building distribution failed. Aborting deployment!" - exit 1 -fi +git push \ + && git checkout $ENVIRONMENT \ + && git rebase master \ + && git push \ + && git checkout master \ + || die "Could not publish changes" diff --git a/scripts/publish b/scripts/publish index a7b04ece6..b7bf9aba7 100755 --- a/scripts/publish +++ b/scripts/publish @@ -5,19 +5,12 @@ function die { exit 1 } -read -p "Major, minor, patch? " VERSION_TYPE -if [[ "$VERSION_TYPE" == "" ]]; then - exit 1 +VERSION_TYPE="" +while [[ "$VERSION_TYPE" != "major" && "$VERSION_TYPE" != "minor" && "$VERSION_TYPE" != "patch" ]]; then + read -p "Major, minor, patch? " VERSION_TYPE fi npm version "$VERSION_TYPE" || die "Invalid version type: $VERSION_TYPE" npm publish -git push \ - && git checkout production \ - && git rebase master \ - && git push \ - && git checkout master \ - || die "Could not publish changes" - -grunt clean build +grunt clean build \ No newline at end of file diff --git a/scripts/s3_upload b/scripts/s3_upload new file mode 100755 index 000000000..b5e7cb5a0 --- /dev/null +++ b/scripts/s3_upload @@ -0,0 +1,39 @@ +#!/bin/bash + +if [[ -e "./aws.config" ]]; then + export AWS_CONFIG_FILE="./aws.config" +else + export AWS_CONFIG_FILE="$HOME/.aws/config" +fi + +ENVIRONMENT="" +while [[ "$1" != "" ]]; do + case "$1" in + "--staging") ENVIRONMENT="staging";; + "--production") ENVIRONMENT="production";; + *) die "Please specify environment: --staging or --production";; + esac +done + +SOURCE_DIR="./dist/" +SITE="new.crafting-guide.com" +[[ "$ENVIRONMENT" == "production" ]] && SITE="crafting-guide.com" +TARGET_DIR="s3://$SITE/" + +S3CMD_CFG="$HOME/.s3cfg" +echo "[default]" > "$S3CMD_CFG" +cat $AWS_CONFIG_FILE | grep "aws_access_key_id" | sed "s/aws_access_key_id/access_key/" >> "$S3CMD_CFG" +cat $AWS_CONFIG_FILE | grep "aws_secret_access_key" | sed "s/aws_secret_access_key/secret_key/" >> "$S3CMD_CFG" + +HEADERS="--add-header=cache-control:max-age=1800" +GZIP="--add-header=content-encoding:gzip" +CMD="sync $SOURCE_DIR $TARGET_DIR -r -P $HEADERS --exclude=*" + +echo "Preparing to upload to S3..." +s3cmd $CMD $GZIP -m 'text/css; charset=utf8' --include="*.css" +s3cmd $CMD $GZIP -m 'text/html; charset=utf8' --include="*.html" +s3cmd $CMD $GZIP -m 'text/javascript; charset=utf8' --include="*.js" +s3cmd $CMD $GZIP -m 'application/json' --include="*.json" +s3cmd $CMD -m 'audio/mpeg3' --include="*.mp3" +s3cmd $CMD -m 'image/png' --include="*.png" +echo "S3 Upload Complete" diff --git a/scripts/server b/scripts/server deleted file mode 100755 index c3bdfa918..000000000 --- a/scripts/server +++ /dev/null @@ -1,64 +0,0 @@ -#!/usr/bin/env coffee -# -# Crafting Guide - serve-build -# -# Copyright (c) 2014-2015 by Redwood Labs -# All rights reserved. -# - -express = require 'express' -fs = require 'fs' -path = require 'path' - -######################################################################################################################## - -ROOT = './dist' -DATA_ROOT = '../crafting-guide-data' -PRERENDER_ROOT = '../crafting-guide-prerender/static' - -CONTENT_TYPE = { - '.cg': 'text/plain' - '.css': 'text/css' - '.html': 'text/html' - '.js': 'text/javascript' - '.json': 'application/json' - '.map': 'application/json' - '.png': 'image/png' - '.ttf': 'application/octet-stream' - '.scss': 'text/css' -} - -######################################################################################################################## - -app = express() - -serveIndex = (request, response)-> - response.set 'Content-Type', 'text/html' - filePath = "#{request.path}index.html".replace('index.htmlindex.html', 'index.html') - fs.stat "#{PRERENDER_ROOT}#{filePath}", (err, stats)-> - if not err? - console.log ">>> #{request.path} ==> #{PRERENDER_ROOT}#{filePath}" - response.sendFile filePath, root:PRERENDER_ROOT - else - console.log ">>> #{request.path} ==> #{ROOT}/app.html" - response.sendFile '/app.html', root:ROOT - -serveData = (request, response)-> - response.set 'Content-Type', CONTENT_TYPE[path.extname request.path] - console.log ">>> #{request.path} ==> #{DATA_ROOT}#{request.path}" - response.sendFile request.path, root:DATA_ROOT - -app.get '/data/*', serveData -app.get '/craft/*', serveIndex -app.get '/login', serveIndex -app.get '*.html', serveIndex -app.get '*/$', serveIndex - -app.get '*', (request, response)-> - response.set 'Content-Type', CONTENT_TYPE[path.extname request.path] - console.log ">>> #{request.path} ==> #{ROOT}#{request.path}" - response.sendFile request.path, root:ROOT - -server = app.listen 8000, '127.0.0.1', -> - console.log "listening at: #{server.address().address}:#{server.address().port}" - diff --git a/scripts/start b/scripts/start new file mode 100755 index 000000000..f506f49b9 --- /dev/null +++ b/scripts/start @@ -0,0 +1,7 @@ +#!/bin/bash + +pushd './build/' &>/dev/null +clear +nodemon ./server.coffee $* +echo '' +popd &>/dev/null diff --git a/scripts/unpublished b/scripts/unpublished deleted file mode 100755 index ec694fed5..000000000 --- a/scripts/unpublished +++ /dev/null @@ -1,27 +0,0 @@ -#!/bin/bash - -MODULE=$(basename $PWD) -QUIET="NO" -while [[ "$1" != "" ]]; do - case "$1" in - "-q") QUIET="YES";; - esac - shift -done - -CHANGES=$(git log --oneline production..master | while read LINE; do echo " $LINE"; done) - -if [[ "$CHANGES" != "" ]]; then - printf "\nUndeployed changes for $MODULE:\n$CHANGES\n\n" -elif [[ "$QUIET" == "NO" ]]; then - printf "No undeployed changes for $MODULE\n\n" -fi - -VERSION=$(cat package.json | grep "version" | sed 's/.*"version": "\(.*\)",$/\1/') -CHANGES=$(git log --oneline "v$VERSION"..master | while read LINE; do echo " $LINE"; done) - -if [[ "$CHANGES" != "" ]]; then - printf "\nUnpublished NPM module changes for $MODULE:\n$CHANGES\n\n" -else - printf "No unpublished NPM module changes for $MODULE\n\n" -fi diff --git a/src/coffee/main.coffee b/src/client/client.coffee similarity index 55% rename from src/coffee/main.coffee rename to src/client/client.coffee index 430b87d7e..18087671e 100644 --- a/src/coffee/main.coffee +++ b/src/client/client.coffee @@ -1,31 +1,36 @@ -### -Crafting Guide - main.coffee +# +# Crafting Guide - client.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### +############################################################################################################ -require './polyfill' +# Allow Node.js-style `global` in addition to `window` +if typeof(global) is 'undefined' + window.global = window -$ = require 'jquery' -CraftingGuideClient = require('crafting-guide-common').CraftingGuideClient -CraftingGuideRouter = require './crafting_guide_router' -FeedbackController = require './controllers/feedback_controller' -Logger = require('crafting-guide-common').Logger -_ = require './underscore_mixins' -backbone = require 'backbone' -marked = require 'marked' -views = require './views' +global._ = require '../common/underscore' +global.$ = require 'jquery' +global.c = require '../common/constants' +global.π = Math.PI +global.ε = 0.0001 +global.w = require 'when' + +global.Backbone = Backbone = require 'backbone' +Backbone.$ = $ + +{Logger} = require 'crafting-guide-common' +global.logger = new Logger + +marked = require 'marked' +marked.setOptions + sanitize: true ######################################################################################################################## -if typeof(global) is 'undefined' - window.global = window - global = window.global - global.hostName = window.location.hostname -global.logger = new Logger - switch global.hostName when 'prerender.crafting-guide.com' global.env = 'prerender' @@ -46,25 +51,23 @@ switch global.hostName else throw new Error "cannot determine the environment of: #{window.location.hostname}" -client = _.extend new CraftingGuideClient(baseUrl:apiBaseUrl), backbone.Events +######################################################################################################################## + +{CraftingGuideClient} = require 'crafting-guide-common' +client = _.extend new CraftingGuideClient(baseUrl:apiBaseUrl), Backbone.Events client.onStatusChanged = (c, oldStatus, newStatus)-> logger.info "Crafting Guide server status changed from #{oldStatus} to #{newStatus}" client.trigger 'change:status', client, oldStatus, newStatus client.trigger 'change', client - -backbone.$ = $ - -marked.setOptions - sanitize: true - -global.feedbackController = new FeedbackController el:'.view__feedback' -feedbackController.render() - -global.router = new CraftingGuideRouter client:client -global.router.loadCurrentUser() -global.router.loadDefaultModPack() - -backbone.history.start pushState:true client.checkStatus() +######################################################################################################################## + +SiteController = require './site/site_controller' +global.site = site = new SiteController client: client +site.render() +site.loadDefaultModPack() +site.loadCurrentUser() + +Backbone.history.start pushState:true logger.info -> "CraftingGuide is ready" diff --git a/src/jade/includes/_google_adsense.jade b/src/client/includes/_google_adsense.jade similarity index 78% rename from src/jade/includes/_google_adsense.jade rename to src/client/includes/_google_adsense.jade index 9d2d87461..f9b4968ea 100644 --- a/src/jade/includes/_google_adsense.jade +++ b/src/client/includes/_google_adsense.jade @@ -1,7 +1,7 @@ //- //- Crafting Guide - _google_adsense.jade //- -//- Copyright (c) 2015 by Redwood Labs +//- Copyright (c) 2015-2016 by Redwood Labs //- All rights reserved. //- diff --git a/src/jade/includes/_google_analytics.jade b/src/client/includes/_google_analytics.jade similarity index 93% rename from src/jade/includes/_google_analytics.jade rename to src/client/includes/_google_analytics.jade index 68dc10a37..63674cbac 100644 --- a/src/jade/includes/_google_analytics.jade +++ b/src/client/includes/_google_analytics.jade @@ -1,7 +1,7 @@ //- //- Crafting Guide - _google_analytics.jade //- -//- Copyright (c) 2014-2015 by Redwood Labs +//- Copyright © 2014-2016 by Redwood Labs //- All rights reserved. //- diff --git a/src/coffee/models/base_model.coffee b/src/client/models/base_model.coffee similarity index 73% rename from src/coffee/models/base_model.coffee rename to src/client/models/base_model.coffee index 035dd025f..8f88c9fff 100644 --- a/src/coffee/models/base_model.coffee +++ b/src/client/models/base_model.coffee @@ -1,19 +1,13 @@ -### -Crafting Guide - base_model.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' -backbone = require 'backbone' -w = require 'when' -{Event} = require '../constants' -{ModelState} = require '../constants' +# +# Crafting Guide - base_model.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# ######################################################################################################################## -module.exports = class BaseModel extends backbone.Model +module.exports = class BaseModel extends Backbone.Model constructor: (attributes={}, options={})-> options.logEvents ?= true @@ -26,15 +20,15 @@ module.exports = class BaseModel extends backbone.Model Object.defineProperty this, name, get:makeGetter(name), set:makeSetter(name) @logEvents = options.logEvents or false - @state = ModelState.unloaded + @state = c.modelState.unloaded @loading = null Object.defineProperties this, - isUnloaded: { get:-> @state is ModelState.unloaded } - isLoading: { get:-> @state is ModelState.loading } - isLoaded: { get:-> @state is ModelState.loaded } - isError: { get:-> @state is ModelState.error } + isUnloaded: { get:-> @state is c.modelState.unloaded } + isLoading: { get:-> @state is c.modelState.loading } + isLoaded: { get:-> @state is c.modelState.loaded } + isError: { get:-> @state is c.modelState.error } # Event Methods ################################################################################ @@ -42,18 +36,18 @@ module.exports = class BaseModel extends backbone.Model try @set @parse text - @state = ModelState.loaded - @trigger Event.change, this - @trigger Event.sync, this + @state = c.modelState.loaded + @trigger c.event.change, this + @trigger c.event.sync, this logger.info => "#{@constructor.name}.#{@cid} loaded successfully" catch e logger.error -> "A parsing error occured: #{e.stack}" @onLoadFailed e.message, 'parsing failed', xhr onLoadFailed: (error, status, xhr)-> - @state = ModelState.error + @state = c.modelState.error logger.error => "#{@constructor.name}.#{@cid} failed to load: status:#{status}, message:#{error}" - @trigger Event.error, this, error + @trigger c.event.error, this, error # Backbone.Model Overrides ##################################################################### @@ -64,8 +58,8 @@ module.exports = class BaseModel extends backbone.Model url = @url() logger.info => "#{@constructor.name}.#{@cid} reading from url: #{url}" - @state = ModelState.loading - @trigger Event.request, this + @state = c.modelState.loading + @trigger c.event.request, this @loading = w.promise (resolve, reject)=> $.ajax url: url diff --git a/src/coffee/models/crafting/crafting_node.coffee b/src/client/models/crafting/crafting_node.coffee similarity index 96% rename from src/coffee/models/crafting/crafting_node.coffee rename to src/client/models/crafting/crafting_node.coffee index 50566dbb6..740ebef66 100644 --- a/src/coffee/models/crafting/crafting_node.coffee +++ b/src/client/models/crafting/crafting_node.coffee @@ -1,11 +1,9 @@ -### -Crafting Guide - crafting_node.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' +# +# Crafting Guide - crafting_node.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# ######################################################################################################################## diff --git a/test/crafting/crafting_node.test.coffee b/src/client/models/crafting/crafting_node.test.coffee similarity index 89% rename from test/crafting/crafting_node.test.coffee rename to src/client/models/crafting/crafting_node.test.coffee index 16223f587..189e719f5 100644 --- a/test/crafting/crafting_node.test.coffee +++ b/src/client/models/crafting/crafting_node.test.coffee @@ -1,11 +1,11 @@ -### -Crafting Node - crafting_node.test.coffee +# +# Crafting Guide - crafting_node.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -fixtures = require './fixtures' +fixtures = require './fixtures.test' ######################################################################################################################## diff --git a/src/coffee/models/crafting/crafting_plan.coffee b/src/client/models/crafting/crafting_plan.coffee similarity index 95% rename from src/coffee/models/crafting/crafting_plan.coffee rename to src/client/models/crafting/crafting_plan.coffee index 65e3e4793..dde3a7aa6 100644 --- a/src/coffee/models/crafting/crafting_plan.coffee +++ b/src/client/models/crafting/crafting_plan.coffee @@ -1,12 +1,11 @@ -### -Crafting Guide - crafting_plan.coffee +# +# Crafting Guide - crafting_plan.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require '../../underscore_mixins' -SimpleInventory = require '../simple_inventory' +SimpleInventory = require './simple_inventory' ######################################################################################################################## diff --git a/test/crafting/crafting_plan.test.coffee b/src/client/models/crafting/crafting_plan.test.coffee similarity index 94% rename from test/crafting/crafting_plan.test.coffee rename to src/client/models/crafting/crafting_plan.test.coffee index 22e08d6ef..512e2746f 100644 --- a/test/crafting/crafting_plan.test.coffee +++ b/src/client/models/crafting/crafting_plan.test.coffee @@ -1,13 +1,13 @@ -### -Crafting Guide - crafting_plan.test.coffee +# +# Crafting Guide - crafting_plan.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -CraftingPlan = require '../../src/coffee/models/crafting/crafting_plan' -fixtures = require './fixtures' -ItemSlug = require '../../src/coffee/models/item_slug' +CraftingPlan = require './crafting_plan' +fixtures = require './fixtures.test' +ItemSlug = require '../game/item_slug' ######################################################################################################################## diff --git a/src/coffee/models/crafting/crafting_step.coffee b/src/client/models/crafting/crafting_step.coffee similarity index 93% rename from src/coffee/models/crafting/crafting_step.coffee rename to src/client/models/crafting/crafting_step.coffee index e50302808..71f7a588c 100644 --- a/src/coffee/models/crafting/crafting_step.coffee +++ b/src/client/models/crafting/crafting_step.coffee @@ -1,11 +1,11 @@ -### -Crafting Guide - crafting_step.coffee +# +# Crafting Guide - crafting_step.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -SimpleInventory = require '../simple_inventory' +SimpleInventory = require './simple_inventory' ######################################################################################################################## diff --git a/src/coffee/models/crafting/craftsman.coffee b/src/client/models/crafting/craftsman.coffee similarity index 90% rename from src/coffee/models/crafting/craftsman.coffee rename to src/client/models/crafting/craftsman.coffee index 04d9ed146..0eca8bea3 100644 --- a/src/coffee/models/crafting/craftsman.coffee +++ b/src/client/models/crafting/craftsman.coffee @@ -1,18 +1,15 @@ -### -Crafting Guide - craftsman.coffee +# +# Crafting Guide - craftsman.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' BaseModel = require '../base_model' -{Event} = require '../../constants' GraphBuilder = require './graph_builder' -Inventory = require '../inventory' +Inventory = require '../game/inventory' PlanBuilder = require './plan_builder' PlanEvaluator = require './plan_evaluator' -w = require 'when' ######################################################################################################################## @@ -46,13 +43,13 @@ module.exports = class Craftsman extends BaseModel reevaluatePlans = _.debounce (=> @reevaluatePlans()), 100 @_have = new Inventory modPack:@_modPack - @_have.on Event.change, reevaluatePlans + @_have.on c.event.change, reevaluatePlans @_want = new Inventory modPack:@_modPack - @_want.on Event.change, reset + @_want.on c.event.change, reset - @on Event.change + ':paused', reset - @on Event.change + ':stage', => logger.info "Craftsman has started #{@stage}..." + @on c.event.change + ':paused', reset + @on c.event.change + ':stage', => logger.info "Craftsman has started #{@stage}..." @on 'scheduleNextWork', => @_scheduleNextWork() @reset() @@ -124,7 +121,7 @@ module.exports = class Craftsman extends BaseModel logger.info => "Craftsman has finished with plans: #{(p.toString() for p in @_plans).join('\n\n')}" - @trigger Event.change, this + @trigger c.event.change, this @trigger 'scheduleNextWork' return @complete diff --git a/test/crafting/fixtures.coffee b/src/client/models/crafting/fixtures.test.coffee similarity index 87% rename from test/crafting/fixtures.coffee rename to src/client/models/crafting/fixtures.test.coffee index e8ee4997d..47d3f2f26 100644 --- a/test/crafting/fixtures.coffee +++ b/src/client/models/crafting/fixtures.test.coffee @@ -1,17 +1,17 @@ -### -Crafting Guide - sample_modpack.coffee +# +# Crafting Guide - fixtures.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -GraphBuilder = require '../../src/coffee/models/crafting/graph_builder' -Inventory = require '../../src/coffee/models/inventory' -ItemSlug = require '../../src/coffee/models/item_slug' -Mod = require '../../src/coffee/models/mod' -ModPack = require '../../src/coffee/models/mod_pack' -ModVersion = require '../../src/coffee/models/mod_version' -PlanBuilder = require '../../src/coffee/models/crafting/plan_builder' +GraphBuilder = require './graph_builder' +Inventory = require '../game/inventory' +ItemSlug = require '../game/item_slug' +Mod = require '../game/mod' +ModPack = require '../game/mod_pack' +ModVersion = require '../game/mod_version' +PlanBuilder = require './plan_builder' ######################################################################################################################## diff --git a/src/coffee/models/crafting/graph_builder.coffee b/src/client/models/crafting/graph_builder.coffee similarity index 88% rename from src/coffee/models/crafting/graph_builder.coffee rename to src/client/models/crafting/graph_builder.coffee index 844463881..f365f09cf 100644 --- a/src/coffee/models/crafting/graph_builder.coffee +++ b/src/client/models/crafting/graph_builder.coffee @@ -1,13 +1,12 @@ -### -Crafting Guide - graph_builder.coffee +# +# Crafting Guide - graph_builder.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -Inventory = require '../inventory' +Inventory = require '../game/inventory' InventoryNode = require './inventory_node' -{Limits} = require '../../constants' ######################################################################################################################## @@ -17,7 +16,7 @@ module.exports = class GraphBuilder if not options.modPack? then throw new Error 'options.modPack is required' if not options.want? then throw new Error 'options.want is required' - @_maximumGraphSize = Limits.maximumGraphSize + @_maximumGraphSize = c.limits.maximumGraphSize @_modPack = options.modPack @_stepCount = 0 @_want = options.want diff --git a/test/crafting/graph_builder.test.coffee b/src/client/models/crafting/graph_builder.test.coffee similarity index 92% rename from test/crafting/graph_builder.test.coffee rename to src/client/models/crafting/graph_builder.test.coffee index 254312b93..241c73ca8 100644 --- a/test/crafting/graph_builder.test.coffee +++ b/src/client/models/crafting/graph_builder.test.coffee @@ -1,12 +1,12 @@ -### -Crafting Guide - crafting_node.test.coffee +# +# Crafting Guide - graph_builder.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -fixtures = require './fixtures' -ItemSlug = require '../../src/coffee/models/item_slug' +fixtures = require './fixtures.test' +ItemSlug = require '../game/item_slug' ######################################################################################################################## diff --git a/src/coffee/models/crafting/inventory_node.coffee b/src/client/models/crafting/inventory_node.coffee similarity index 94% rename from src/coffee/models/crafting/inventory_node.coffee rename to src/client/models/crafting/inventory_node.coffee index 9869c910b..8f5555e32 100644 --- a/src/coffee/models/crafting/inventory_node.coffee +++ b/src/client/models/crafting/inventory_node.coffee @@ -1,9 +1,9 @@ -### -Crafting Guide - crafting_plan_node.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - inventory_node.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# CraftingNode = require './crafting_node' ItemNode = require './item_node' diff --git a/src/coffee/models/crafting/item_node.coffee b/src/client/models/crafting/item_node.coffee similarity index 96% rename from src/coffee/models/crafting/item_node.coffee rename to src/client/models/crafting/item_node.coffee index 83fa2a2c2..b059cdf52 100644 --- a/src/coffee/models/crafting/item_node.coffee +++ b/src/client/models/crafting/item_node.coffee @@ -1,9 +1,9 @@ -### -Crafting Guide - item_node.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - item_node.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# CraftingNode = require './crafting_node' RecipeNode = require './recipe_node' diff --git a/src/coffee/models/crafting/plan_builder.coffee b/src/client/models/crafting/plan_builder.coffee similarity index 93% rename from src/coffee/models/crafting/plan_builder.coffee rename to src/client/models/crafting/plan_builder.coffee index 972cc8ce4..a8687acc9 100644 --- a/src/coffee/models/crafting/plan_builder.coffee +++ b/src/client/models/crafting/plan_builder.coffee @@ -1,15 +1,14 @@ -### -Crafting Plan - plan_builder.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - plan_builder.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# CraftingNode = require './crafting_node' CraftingPlan = require './crafting_plan' CraftingStep = require './crafting_step' -Inventory = require '../inventory' -{Limits} = require '../../constants' +Inventory = require '../game/inventory' ######################################################################################################################## @@ -24,7 +23,7 @@ module.exports = class PlanBuilder @_choiceNodes = [] @_complete = false - @_maxPlanCount = Limits.maximumPlanCount + @_maxPlanCount = c.limits.maximumPlanCount @_modPack = modPack @_plans = [] @_rootNode = rootNode diff --git a/test/crafting/plan_builder.test.coffee b/src/client/models/crafting/plan_builder.test.coffee similarity index 86% rename from test/crafting/plan_builder.test.coffee rename to src/client/models/crafting/plan_builder.test.coffee index f33d8e3b9..f81a97cd5 100644 --- a/test/crafting/plan_builder.test.coffee +++ b/src/client/models/crafting/plan_builder.test.coffee @@ -1,12 +1,12 @@ -### -Crafting Guide - plan_builder.test.coffee +# +# Crafting Guide - plan_builder.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -fixtures = require './fixtures' -PlanBuilder = require '../../src/coffee/models/crafting/plan_builder' +fixtures = require './fixtures.test' +PlanBuilder = require './plan_builder' ######################################################################################################################## diff --git a/src/coffee/models/crafting/plan_evaluator.coffee b/src/client/models/crafting/plan_evaluator.coffee similarity index 96% rename from src/coffee/models/crafting/plan_evaluator.coffee rename to src/client/models/crafting/plan_evaluator.coffee index 6525c916b..0676976b1 100644 --- a/src/coffee/models/crafting/plan_evaluator.coffee +++ b/src/client/models/crafting/plan_evaluator.coffee @@ -1,9 +1,9 @@ -### -Crafting Guide - plan_evaluator.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - plan_evaluator.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# ######################################################################################################################## diff --git a/test/crafting/plan_evaluator.test.coffee b/src/client/models/crafting/plan_evaluator.test.coffee similarity index 89% rename from test/crafting/plan_evaluator.test.coffee rename to src/client/models/crafting/plan_evaluator.test.coffee index 19d82564a..70f87b91d 100644 --- a/test/crafting/plan_evaluator.test.coffee +++ b/src/client/models/crafting/plan_evaluator.test.coffee @@ -1,14 +1,14 @@ -### -Crafting Guide - plan_evaluator.test.coffee +# +# Crafting Guide - plan_evaluator.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -CraftingPlan = require '../../src/coffee/models/crafting/crafting_plan' -fixtures = require './fixtures' -Inventory = require '../../src/coffee/models/inventory' -PlanEvaluator = require '../../src/coffee/models/crafting/plan_evaluator' +CraftingPlan = require './crafting_plan' +fixtures = require './fixtures.test' +Inventory = require '../game/inventory' +PlanEvaluator = require './plan_evaluator' ######################################################################################################################## diff --git a/src/coffee/models/crafting/recipe_node.coffee b/src/client/models/crafting/recipe_node.coffee similarity index 93% rename from src/coffee/models/crafting/recipe_node.coffee rename to src/client/models/crafting/recipe_node.coffee index a782c01b8..b262a4141 100644 --- a/src/coffee/models/crafting/recipe_node.coffee +++ b/src/client/models/crafting/recipe_node.coffee @@ -1,14 +1,14 @@ -### -Crafting Guide - recipe_node.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - recipe_node.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# CraftingNode = require './crafting_node' -Item = require '../item' +Item = require '../game/item' # ItemNode = require './item_node' # don't include here, causes a cycle -ItemSlug = require '../item_slug' +ItemSlug = require '../game/item_slug' ######################################################################################################################## diff --git a/src/coffee/models/simple_inventory.coffee b/src/client/models/crafting/simple_inventory.coffee similarity index 96% rename from src/coffee/models/simple_inventory.coffee rename to src/client/models/crafting/simple_inventory.coffee index ffe0248df..240134654 100644 --- a/src/coffee/models/simple_inventory.coffee +++ b/src/client/models/crafting/simple_inventory.coffee @@ -1,13 +1,12 @@ -### -Crafting Guide - inventory.coffee +# +# Crafting Guide - simple_inventory.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -ItemSlug = require './item_slug' -SimpleStack = require './simple_stack' -_ = require 'underscore' +ItemSlug = require '../game/item_slug' +SimpleStack = require './simple_stack' ######################################################################################################################## diff --git a/src/client/models/crafting/simple_stack.coffee b/src/client/models/crafting/simple_stack.coffee new file mode 100644 index 000000000..361eedb4b --- /dev/null +++ b/src/client/models/crafting/simple_stack.coffee @@ -0,0 +1,33 @@ +# +# Crafting Guide - simple_stack.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +ItemSlug = require '../game/item_slug' + +######################################################################################################################## + +module.exports = class Stack + + constructor: (attributes={}, options={})-> + if not attributes.itemSlug? then throw new Error 'attributes.itemSlug is required' + attributes.quantity ?= 1 + + @itemSlug = attributes.itemSlug + @quantity = attributes.quantity + + # Class Methods ################################################################################ + + @compare: (a, b)-> + if a? and not b? then return -1 + if not a? and b? then return +1 + if a.quantity isnt b.quantity + return if a.quantity > b.quantity then -1 else +1 + return ItemSlug.compare a.itemSlug, b.itemSlug + + # Object Overrides ############################################################################# + + toString: -> + return "#{@quantity} #{@itemSlug}" diff --git a/test/event_recorder.coffee b/src/client/models/event_recorder.coffee similarity index 67% rename from test/event_recorder.coffee rename to src/client/models/event_recorder.coffee index 973cd4af9..27d07947a 100644 --- a/test/event_recorder.coffee +++ b/src/client/models/event_recorder.coffee @@ -17,12 +17,20 @@ module.exports = class EventRecorder @model = model @events = [] - Object.defineProperty this, 'names', get:-> e.event for e in @events - @model.on 'all', (event, model, args...)=> logger.verbose -> "#{model?.constructor?.name}(#{model?.cid}) emitted #{event} with args: #{util.inspect(args)}" @events.push id:model?.cid, event:event, args:args + # Public Methods ############################################################################### + reset: -> @events = [] + + # Property Methods ############################################################################# + + getNames: -> + return (e.event for e in @events) + + Object.defineProperties @prototype, + names: {get:@prototype.getNames} diff --git a/src/coffee/models/inventory.coffee b/src/client/models/game/inventory.coffee similarity index 83% rename from src/coffee/models/inventory.coffee rename to src/client/models/game/inventory.coffee index 2b814395d..96d4d8368 100644 --- a/src/coffee/models/inventory.coffee +++ b/src/client/models/game/inventory.coffee @@ -1,16 +1,13 @@ -### -Crafting Guide - inventory.coffee +# +# Crafting Guide - inventory.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' -ItemSlug = require './item_slug' -Stack = require './stack' -_ = require 'underscore' -{Event} = require '../constants' -{RequiredMods} = require '../constants' +BaseModel = require '../base_model' +ItemSlug = require './item_slug' +Stack = require './stack' ######################################################################################################################## @@ -36,21 +33,21 @@ module.exports = class Inventory extends BaseModel return this unless quantity > 0 @_add itemSlug, quantity - @trigger Event.add, this, itemSlug, quantity - @trigger Event.change, this + @trigger c.event.add, this, itemSlug, quantity + @trigger c.event.change, this return this addInventory: (inventory)-> inventory.each (stack)=> @_add stack.itemSlug, stack.quantity - @trigger Event.change, this + @trigger c.event.change, this return this clear: (options={})-> @_stacks = {} @_itemSlugs = [] - @trigger Event.change, this + @trigger c.event.change, this clone: -> inventory = new Inventory @@ -103,10 +100,10 @@ module.exports = class Inventory extends BaseModel @_stacks = {} for stack in newStacks @_stacks[stack.itemSlug] = stack - @listenTo stack, Event.change, => @trigger Event.change, this + @listenTo stack, c.event.change, => @trigger c.event.change, this @_sort() - @trigger Event.change, this + @trigger c.event.change, this pop: -> itemSlug = @_itemSlugs.pop() @@ -115,8 +112,8 @@ module.exports = class Inventory extends BaseModel stack = @_stacks[itemSlug] delete @_stacks[itemSlug] - @trigger Event.remove, this, stack.itemSlug, stack.quantity - @trigger Event.change, this + @trigger c.event.remove, this, stack.itemSlug, stack.quantity + @trigger c.event.change, this return stack quantityOf: (itemSlug)-> @@ -140,8 +137,8 @@ module.exports = class Inventory extends BaseModel delete @_stacks[itemSlug] @_itemSlugs = (s for s in @_itemSlugs when not ItemSlug.equal(s, itemSlug)) - @trigger Event.remove, this, itemSlug, quantity - @trigger Event.change, this + @trigger c.event.remove, this, itemSlug, quantity + @trigger c.event.change, this return this # Parsing Methods ############################################################################## @@ -184,18 +181,16 @@ module.exports = class Inventory extends BaseModel # Property Methods ############################################################################# - getIsEmpty: -> - return @_itemSlugs.length is 0 - - getTotalQuantity: -> - total = 0 - @each (stack)-> - total += stack.quantity - return total - Object.defineProperties @prototype, - isEmpty: { get:@prototype.getIsEmpty } - totalQuantity: { get:@prototype.getTotalQuantity } + isEmpty: + get: -> @_itemSlugs.length is 0 + + totalQuantity: + get: -> + total = 0 + @each (stack)-> + total += stack.quantity + return total # Object Overrides ############################################################################# @@ -221,7 +216,7 @@ module.exports = class Inventory extends BaseModel stack = @_stacks[itemSlug] if not stack? stack = new Stack itemSlug:itemSlug, quantity:quantity - @listenTo stack, Event.change, => @trigger Event.change, this + @listenTo stack, c.event.change, => @trigger c.event.change, this @_stacks[itemSlug] = stack @_itemSlugs.push itemSlug @_sort() diff --git a/test/inventory.test.coffee b/src/client/models/game/inventory.test.coffee similarity index 93% rename from test/inventory.test.coffee rename to src/client/models/game/inventory.test.coffee index d699d1184..78b704a0f 100644 --- a/test/inventory.test.coffee +++ b/src/client/models/game/inventory.test.coffee @@ -1,15 +1,14 @@ -### +# # Crafting Guide - inventory.test.coffee # -# Copyright (c) 2014-2015 by Redwood Labs +# Copyright © 2014-2016 by Redwood Labs # All rights reserved. -### +# -{Event} = require '../src/coffee/constants' -EventRecorder = require './event_recorder' -Inventory = require '../src/coffee/models/inventory' -Item = require '../src/coffee/models/item' -ItemSlug = require '../src/coffee/models/item_slug' +EventRecorder = require '../event_recorder' +Inventory = require './inventory' +Item = require './item' +ItemSlug = require './item_slug' ######################################################################################################################## @@ -45,7 +44,7 @@ describe 'inventory.coffee', -> it 'emits the proper events', -> events = new EventRecorder inventory inventory.add ItemSlug.slugify('iron_ingot'), 10 - events.names.should.eql [Event.add, Event.change] + events.names.should.eql [c.event.add, c.event.change] describe 'addInventory', -> @@ -185,7 +184,7 @@ describe 'inventory.coffee', -> it 'triggers the right events', -> events = new EventRecorder inventory result = inventory.pop() - events.names.should.eql [Event.remove, Event.change] + events.names.should.eql [c.event.remove, c.event.change] describe 'remove', -> @@ -211,4 +210,4 @@ describe 'inventory.coffee', -> it 'emits the proper events', -> events = new EventRecorder inventory inventory.remove 'wool' - events.names.should.eql [Event.change, Event.remove, Event.change] + events.names.should.eql [c.event.change, c.event.remove, c.event.change] diff --git a/src/coffee/models/item.coffee b/src/client/models/game/item.coffee similarity index 85% rename from src/coffee/models/item.coffee rename to src/client/models/game/item.coffee index 34cc38dc7..9ab2545aa 100644 --- a/src/coffee/models/item.coffee +++ b/src/client/models/game/item.coffee @@ -1,16 +1,14 @@ -### -Crafting Guide - item.coffee +# +# Crafting Guide - item.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' +BaseModel = require '../base_model' ItemSlug = require './item_slug' Recipe = require './recipe' -{Event} = require '../constants' {StringBuilder} = require 'crafting-guide-common' -{Url} = require '../constants' ######################################################################################################################## @@ -33,7 +31,7 @@ module.exports = class Item extends BaseModel options.logEvents ?= false super attributes, options - @on Event.change + ':modVersion', => + @on c.event.change + ':modVersion', => @_isCraftable = null @slug.mod = @modVersion?.modSlug @@ -47,7 +45,7 @@ module.exports = class Item extends BaseModel return 0 unparse: -> - ItemParser = require './item_parser' # to avoid require cycles + ItemParser = require '../parsing/item_parser' # to avoid require cycles @_parser ?= new ItemParser model:this return @_parser.unparse() @@ -67,14 +65,14 @@ module.exports = class Item extends BaseModel # Backbone.Model Overrides ##################################################################### parse: (text)-> - ItemParser = require './item_parser' # to avoid require cycles + ItemParser = require '../parsing/item_parser' # to avoid require cycles @_parser ?= new ItemParser model:this @_parser.parse text return null # prevent calling `set` url: -> - return Url.itemData modSlug:@slug.mod, itemSlug:@slug.item + return c.url.itemData modSlug:@slug.mod, itemSlug:@slug.item # Object Overrides ############################################################################# diff --git a/src/coffee/models/item_slug.coffee b/src/client/models/game/item_slug.coffee similarity index 71% rename from src/coffee/models/item_slug.coffee rename to src/client/models/game/item_slug.coffee index 2a90be171..78e2ecb1f 100644 --- a/src/coffee/models/item_slug.coffee +++ b/src/client/models/game/item_slug.coffee @@ -1,12 +1,9 @@ -### -Crafting Guide - item_slug.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' -{RequiredMods} = require '../constants' +# +# Crafting Guide - item_slug.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# ######################################################################################################################## @@ -68,33 +65,27 @@ module.exports = class ItemSlug # Property Methods ############################################################################# - getIsQualified: -> - return @_mod? - - getItem: -> - return @_item - - setItem: (item)-> - if not item? then throw new Error 'item is required' - @_item = item - - @mod = @mod # reset @_qualified - - getMod: -> - return @_mod - - setMod: (mod)-> - @_mod = mod - @_qualified = if @_mod? then _.composeSlugs(@_mod, @_item) else @_item - - getQualified: -> - return @_qualified - Object.defineProperties @prototype, - isQualified: { get:@prototype.getIsQualified } - mod: { get:@prototype.getMod, set:@prototype.setMod } - item: { get:@prototype.getItem, set:@prototype.setItem } - qualified: { get:@prototype.getQualified } + isQualified: + get: -> @_mod? + + item: + get: -> @_item + + set: (newItem)-> + if not newItem? then throw new Error 'item is required' + @_item = newItem + @mod = @mod # reset @_qualified + + mod: + get: -> @_mod + + set: (newMod)-> + @_mod = newMod + @_qualified = if @_mod? then _.composeSlugs(@_mod, @_item) else @_item + + qualified: + get: -> @_qualified # Object Overrides ############################################################################# diff --git a/test/item_slug.test.coffee b/src/client/models/game/item_slug.test.coffee similarity index 96% rename from test/item_slug.test.coffee rename to src/client/models/game/item_slug.test.coffee index 2d942b040..106b8ce5a 100644 --- a/test/item_slug.test.coffee +++ b/src/client/models/game/item_slug.test.coffee @@ -1,11 +1,11 @@ -### -Crafting Guide - item_slug.coffee +# +# Crafting Guide - item_slug.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -ItemSlug = require '../src/coffee/models/item_slug' +ItemSlug = require './item_slug' ######################################################################################################################## diff --git a/src/coffee/models/mod.coffee b/src/client/models/game/mod.coffee similarity index 85% rename from src/coffee/models/mod.coffee rename to src/client/models/game/mod.coffee index 00d3f1cd6..8e613d821 100644 --- a/src/coffee/models/mod.coffee +++ b/src/client/models/game/mod.coffee @@ -1,15 +1,11 @@ -### -Crafting Guide - mod.coffee +# +# Crafting Guide - mod.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' -BaseModel = require './base_model' -{Event} = require '../constants' -{RequiredMods} = require '../constants' -{Url} = require '../constants' +BaseModel = require '../base_model' ######################################################################################################################## @@ -33,7 +29,7 @@ module.exports = class Mod extends BaseModel @_modVersions = [] @_tutorials = [] - @once Event.sync, => @_verifyActiveModVersion() + @once c.event.sync, => @_verifyActiveModVersion() # Class Methods ################################################################################## @@ -44,8 +40,8 @@ module.exports = class Mod extends BaseModel # Public Methods ################################################################################# compareTo: (that)-> - thisRequired = this.slug in RequiredMods - thatRequired = that.slug in RequiredMods + thisRequired = this.slug in c.requiredMods + thatRequired = that.slug in c.requiredMods if thisRequired isnt thatRequired return -1 if thisRequired @@ -76,8 +72,8 @@ module.exports = class Mod extends BaseModel @_activeVersion = version @_activateModVersion null - @trigger Event.change + ':activeVersion', this, @_activeVersion - @trigger Event.change, this + @trigger c.event.change + ':activeVersion', this, @_activeVersion + @trigger c.event.change, this else for modVersion in @_modVersions if version is modVersion.version @@ -85,12 +81,15 @@ module.exports = class Mod extends BaseModel break @_activeVersion = version - @trigger Event.change + ':activeVersion', this, @_activeVersion - @trigger Event.change, this + @trigger c.event.change + ':activeVersion', this, @_activeVersion + @trigger c.event.change, this enabled: get: -> @_activeModVersion? + modVersions: + get: -> @_modVersions[..] + tutorials: get: -> @getAllTutorials() @@ -129,12 +128,12 @@ module.exports = class Mod extends BaseModel return if @_modVersions.indexOf(modVersion) isnt -1 @_modVersions.push modVersion - @listenTo modVersion, Event.change, => @trigger Event.change, this + @listenTo modVersion, c.event.change, => @trigger c.event.change, this modVersion.mod = this - @trigger Event.add + ':modVersion', modVersion, this - @trigger Event.change + ':version', modVersion, this - @trigger Event.change, this + @trigger c.event.add + ':modVersion', modVersion, this + @trigger c.event.change + ':version', modVersion, this + @trigger c.event.change, this if not @activeVersion? then @activeVersion = modVersion.version if modVersion.version is @_activeVersion then @_activateModVersion modVersion @@ -198,21 +197,21 @@ module.exports = class Mod extends BaseModel # Backbone.Model Overrides ##################################################################### parse: (text)-> - ModParser = require './mod_parser' # to avoid require cycles + ModParser = require '../parsing/mod_parser' # to avoid require cycles @_parser ?= new ModParser model:this @_parser.parse text return null # prevent calling `set` url: -> - return Url.modData modSlug:@slug + return c.url.modData modSlug:@slug # Private Methods ############################################################################## _activateModVersion: (modVersion)-> if @_activeModVersion? then @stopListening @_activeModVersion @_activeModVersion = modVersion - @trigger Event.change + ':activeModVersion', this, @_activeModVersion + @trigger c.event.change + ':activeModVersion', this, @_activeModVersion logger.verbose => "#{@slug} switched to version #{@_activeVersion}" diff --git a/test/mod.test.coffee b/src/client/models/game/mod.test.coffee similarity index 85% rename from test/mod.test.coffee rename to src/client/models/game/mod.test.coffee index 22162939c..bbfd66776 100644 --- a/test/mod.test.coffee +++ b/src/client/models/game/mod.test.coffee @@ -1,11 +1,11 @@ -### -Crafting Guide - mod.test.coffee +# +# Crafting Guide - mod.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -Mod = require '../src/coffee/models/mod' +Mod = require './mod' ######################################################################################################################## diff --git a/src/coffee/models/mod_pack.coffee b/src/client/models/game/mod_pack.coffee similarity index 82% rename from src/coffee/models/mod_pack.coffee rename to src/client/models/game/mod_pack.coffee index d7bdfa71a..3ff282fce 100644 --- a/src/coffee/models/mod_pack.coffee +++ b/src/client/models/game/mod_pack.coffee @@ -1,17 +1,14 @@ -### -Crafting Guide - mod_pack.coffee +# +# Crafting Guide - mod_pack.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' -{DefaultModVersions} = require '../constants' -{Event} = require '../constants' -Inventory = require './inventory' -ModVersionParser = require './mod_version_parser' -Recipe = require './recipe' -{Url} = require '../constants' +BaseModel = require '../base_model' +Inventory = require './inventory' +ModVersionParser = require '../parsing/mod_version_parser' +Recipe = require './recipe' ######################################################################################################################## @@ -23,7 +20,7 @@ module.exports = class ModPack extends BaseModel @_mods = [] @_cache = {} - @on Event.change, => @_cache = {} + @on c.event.change, => @_cache = {} # Item Methods ################################################################################# @@ -84,10 +81,10 @@ module.exports = class ModPack extends BaseModel else craftingUrlInventory.add itemSlug - result.craftingUrl = Url.crafting inventoryText:craftingUrlInventory.unparse() - result.iconUrl = Url.itemIcon result - result.itemUrl = Url.item result - result.modName = @getMod(result.modSlug).name + result.craftingUrl = c.url.crafting inventoryText:craftingUrlInventory.unparse() + result.iconUrl = c.url.itemIcon result + result.itemUrl = c.url.item result + result.modName = @getMod(result.modSlug).name return result qualifySlug: (itemSlug)-> @@ -105,12 +102,12 @@ module.exports = class ModPack extends BaseModel mod.modPack = this @_mods.push mod - @listenTo mod, Event.change, (modVersion)=> @_onModVersionLoaded modVersion - @trigger Event.add + ':mod', mod, this + @listenTo mod, c.event.change, (modVersion)=> @_onModVersionLoaded modVersion + @trigger c.event.add + ':mod', mod, this @_mods.sort (a, b)-> a.compareTo b - @trigger Event.sort + ':mod', this - @trigger Event.change, this + @trigger c.event.sort + ':mod', this + @trigger c.event.change, this return this @@ -175,5 +172,5 @@ module.exports = class ModPack extends BaseModel return if working - @trigger Event.change, this - @trigger Event.sync, this + @trigger c.event.change, this + @trigger c.event.sync, this diff --git a/test/mod_pack.test.coffee b/src/client/models/game/mod_pack.test.coffee similarity index 92% rename from test/mod_pack.test.coffee rename to src/client/models/game/mod_pack.test.coffee index a6a28cb23..ade40cfc5 100644 --- a/test/mod_pack.test.coffee +++ b/src/client/models/game/mod_pack.test.coffee @@ -1,15 +1,15 @@ -### -Crafting Guide - mod_pack.test.coffee +# +# Crafting Guide - mod_pack.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -Item = require '../src/coffee/models/item' -ItemSlug = require '../src/coffee/models/item_slug' -Mod = require '../src/coffee/models/mod' -ModPack = require '../src/coffee/models/mod_pack' -ModVersion = require '../src/coffee/models/mod_version' +Item = require './item' +ItemSlug = require './item_slug' +Mod = require './mod' +ModPack = require './mod_pack' +ModVersion = require './mod_version' ######################################################################################################################## diff --git a/src/coffee/models/mod_version.coffee b/src/client/models/game/mod_version.coffee similarity index 90% rename from src/coffee/models/mod_version.coffee rename to src/client/models/game/mod_version.coffee index 469b9857e..d2c1503f8 100644 --- a/src/coffee/models/mod_version.coffee +++ b/src/client/models/game/mod_version.coffee @@ -1,18 +1,14 @@ -### -Crafting Guide - mod_version.coffee +# +# Crafting Guide - mod_version.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' -Item = require './item' -ItemSlug = require './item_slug' -Recipe = require './recipe' -_ = require 'underscore' -{Event} = require '../constants' -{RequiredMods} = require '../constants' -{Url} = require '../constants' +BaseModel = require '../base_model' +Item = require './item' +ItemSlug = require './item_slug' +Recipe = require './recipe' ######################################################################################################################## @@ -183,14 +179,14 @@ module.exports = class ModVersion extends BaseModel # Backbone.Model Overrides ##################################################################### parse: (text)-> - ModVersionParser = require './mod_version_parser' # to avoid require cycles + ModVersionParser = require '../parsing/mod_version_parser' # to avoid require cycles @_parser ?= new ModVersionParser model:this @_parser.parse text return null # prevent calling `set` url: -> - return Url.modVersionData modSlug:@modSlug, modVersion:@version + return c.url.modVersionData modSlug:@modSlug, modVersion:@version # Object Overrides ############################################################################# diff --git a/test/mod_version.test.coffee b/src/client/models/game/mod_version.test.coffee similarity index 93% rename from test/mod_version.test.coffee rename to src/client/models/game/mod_version.test.coffee index 46346bcd3..cba6d85d5 100644 --- a/test/mod_version.test.coffee +++ b/src/client/models/game/mod_version.test.coffee @@ -1,13 +1,13 @@ -### -Crafting Guide - mod_version.test.coffee +# +# Crafting Guide - mod_version.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -Item = require '../src/coffee/models/item' -ItemSlug = require '../src/coffee/models/item_slug' -ModVersion = require '../src/coffee/models/mod_version' +Item = require './item' +ItemSlug = require './item_slug' +ModVersion = require './mod_version' ######################################################################################################################## diff --git a/src/coffee/models/multiblock.coffee b/src/client/models/game/multiblock.coffee similarity index 93% rename from src/coffee/models/multiblock.coffee rename to src/client/models/game/multiblock.coffee index 333fb34e6..273dfd702 100644 --- a/src/coffee/models/multiblock.coffee +++ b/src/client/models/game/multiblock.coffee @@ -1,12 +1,11 @@ -### -Crafting Guide - multiblock.coffee +# +# Crafting Guide - multiblock.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -_ = require '../underscore_mixins' -BaseModel = require './base_model' +BaseModel = require '../base_model' Inventory = require './inventory' ######################################################################################################################## diff --git a/test/multiblock.test.coffee b/src/client/models/game/multiblock.test.coffee similarity index 90% rename from test/multiblock.test.coffee rename to src/client/models/game/multiblock.test.coffee index 168635c93..777db1baa 100644 --- a/test/multiblock.test.coffee +++ b/src/client/models/game/multiblock.test.coffee @@ -1,14 +1,14 @@ -### -Crafting Guide - multiblock.test.coffee +# +# Crafting Guide - multiblock.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -ItemSlug = require '../src/coffee/models/item_slug' -Mod = require '../src/coffee/models/multiblock' -Multiblock = require '../src/coffee/models/multiblock' -Stack = require '../src/coffee/models/stack' +ItemSlug = require './item_slug' +Mod = require './mod' +Multiblock = require './multiblock' +Stack = require './stack' ######################################################################################################################## diff --git a/src/coffee/models/recipe.coffee b/src/client/models/game/recipe.coffee similarity index 93% rename from src/coffee/models/recipe.coffee rename to src/client/models/game/recipe.coffee index 5ed0513b3..fb59bbbdd 100644 --- a/src/coffee/models/recipe.coffee +++ b/src/client/models/game/recipe.coffee @@ -1,14 +1,13 @@ -### -Crafting Guide - recipe.coffee +# +# Crafting Guide - recipe.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' +BaseModel = require '../base_model' ItemSlug = require './item_slug' Stack = require './stack' -{Event} = require '../constants' {StringBuilder} = require 'crafting-guide-common' ######################################################################################################################## @@ -38,8 +37,8 @@ module.exports = class Recipe extends BaseModel @_computeQuantities attributes.pattern - @on Event.change + ':modVersion', => @_slug = null - @on Event.change + ':pattern', => @_patternCache = null + @on c.event.change + ':modVersion', => @_slug = null + @on c.event.change + ':pattern', => @_patternCache = null # Class Methods ################################################################################ @@ -104,12 +103,9 @@ module.exports = class Recipe extends BaseModel if modPack?.findItemByName(@condition.noun)? result = true else if @condition.verb is 'mod' - if not modPack? - result = true - else - modPack.eachMod (mod)=> - if mod.name is @condition.noun - result = true + modPack.eachMod (mod)-> + if mod.name is @condition.noun + result = true if @condition.inverted then result = not result return result diff --git a/test/recipe.test.coffee b/src/client/models/game/recipe.test.coffee similarity index 91% rename from test/recipe.test.coffee rename to src/client/models/game/recipe.test.coffee index 741fb3557..38daf33de 100644 --- a/test/recipe.test.coffee +++ b/src/client/models/game/recipe.test.coffee @@ -1,14 +1,14 @@ -### -Crafting Guide - recipe.test.coffee +# +# Crafting Guide - recipe.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -Item = require '../src/coffee/models/item' -ItemSlug = require '../src/coffee/models/item_slug' -Recipe = require '../src/coffee/models/recipe' -Stack = require '../src/coffee/models/stack' +Item = require './item' +ItemSlug = require './item_slug' +Recipe = require './recipe' +Stack = require './stack' ######################################################################################################################## diff --git a/src/coffee/models/simple_stack.coffee b/src/client/models/game/simple_stack.coffee similarity index 89% rename from src/coffee/models/simple_stack.coffee rename to src/client/models/game/simple_stack.coffee index 69d6b09f3..d077f4c58 100644 --- a/src/coffee/models/simple_stack.coffee +++ b/src/client/models/game/simple_stack.coffee @@ -1,9 +1,9 @@ -### -Crafting Guide - simple_stack.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - simple_stack.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# ItemSlug = require './item_slug' diff --git a/src/coffee/models/stack.coffee b/src/client/models/game/stack.coffee similarity index 80% rename from src/coffee/models/stack.coffee rename to src/client/models/game/stack.coffee index 161988839..6797330dd 100644 --- a/src/coffee/models/stack.coffee +++ b/src/client/models/game/stack.coffee @@ -1,11 +1,11 @@ -### -Crafting Guide - stack.coffee +# +# Crafting Guide - stack.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' +BaseModel = require '../base_model' ######################################################################################################################## diff --git a/src/coffee/models/parser_versions/command_parser_version_base.coffee b/src/client/models/parsing/command_parser_version_base.coffee similarity index 96% rename from src/coffee/models/parser_versions/command_parser_version_base.coffee rename to src/client/models/parsing/command_parser_version_base.coffee index c8ec2ddaf..00e0e0ab0 100644 --- a/src/coffee/models/parser_versions/command_parser_version_base.coffee +++ b/src/client/models/parsing/command_parser_version_base.coffee @@ -1,11 +1,10 @@ -### -Crafting Guide - command_parser_version_base.coffee +# +# Crafting Guide - command_parser_version_base.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' {StringBuilder} = require 'crafting-guide-common' ######################################################################################################################## diff --git a/test/parser_versions/command_parser_version_base.test.coffee b/src/client/models/parsing/command_parser_version_base.test.coffee similarity index 87% rename from test/parser_versions/command_parser_version_base.test.coffee rename to src/client/models/parsing/command_parser_version_base.test.coffee index c1c34ad6c..903e5adef 100644 --- a/test/parser_versions/command_parser_version_base.test.coffee +++ b/src/client/models/parsing/command_parser_version_base.test.coffee @@ -1,11 +1,11 @@ -### -Crafting Guide - command_parser_version_base.test.coffee +# +# Crafting Guide - command_parser_version_base.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -CommandParserVersionBase = require '../../src/coffee/models/parser_versions/command_parser_version_base' +CommandParserVersionBase = require './command_parser_version_base' ######################################################################################################################## diff --git a/src/coffee/models/item_parser.coffee b/src/client/models/parsing/item_parser.coffee similarity index 72% rename from src/coffee/models/item_parser.coffee rename to src/client/models/parsing/item_parser.coffee index f3cc5be07..eb0d5cfa0 100644 --- a/src/coffee/models/item_parser.coffee +++ b/src/client/models/parsing/item_parser.coffee @@ -1,12 +1,12 @@ -### -Crafting Guide - item_parser.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - item_parser.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# VersionedParserBase = require './versioned_parser_base' -ItemParserV1 = require './parser_versions/item_parser_v1' +ItemParserV1 = require './item_parser_v1' ######################################################################################################################## diff --git a/src/coffee/models/parser_versions/item_parser_v1.coffee b/src/client/models/parsing/item_parser_v1.coffee similarity index 95% rename from src/coffee/models/parser_versions/item_parser_v1.coffee rename to src/client/models/parsing/item_parser_v1.coffee index 6cc05e8c2..32c9a6a95 100644 --- a/src/coffee/models/parser_versions/item_parser_v1.coffee +++ b/src/client/models/parsing/item_parser_v1.coffee @@ -1,9 +1,9 @@ -### -Crafting Guide - item_parser_v1.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - item_parser_v1.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# CommandParserVersionBase = require './command_parser_version_base' diff --git a/test/parser_versions/item_version_parser_v1.test.coffee b/src/client/models/parsing/item_parser_v1.test.coffee similarity index 91% rename from test/parser_versions/item_version_parser_v1.test.coffee rename to src/client/models/parsing/item_parser_v1.test.coffee index 386aaf272..25f6e7f5c 100644 --- a/test/parser_versions/item_version_parser_v1.test.coffee +++ b/src/client/models/parsing/item_parser_v1.test.coffee @@ -1,13 +1,12 @@ -### -Crafting Guide - item_parser_v1.test.coffee +# +# Crafting Guide - item_parser_v1.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -Item = require '../../src/coffee/models/item' -ItemParserV1 = require '../../src/coffee/models/parser_versions/item_parser_v1' -_ = require 'underscore' +Item = require '../game/item' +ItemParserV1 = require './item_parser_v1' ######################################################################################################################## diff --git a/src/coffee/models/mod_parser.coffee b/src/client/models/parsing/mod_parser.coffee similarity index 72% rename from src/coffee/models/mod_parser.coffee rename to src/client/models/parsing/mod_parser.coffee index e28aa34d7..03f368b96 100644 --- a/src/coffee/models/mod_parser.coffee +++ b/src/client/models/parsing/mod_parser.coffee @@ -1,12 +1,12 @@ -### -Crafting Guide - mod_parser.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - mod_parser.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# VersionedParserBase = require './versioned_parser_base' -ModParserV1 = require './parser_versions/mod_parser_v1' +ModParserV1 = require './mod_parser_v1' ######################################################################################################################## diff --git a/src/coffee/models/parser_versions/mod_parser_v1.coffee b/src/client/models/parsing/mod_parser_v1.coffee similarity index 93% rename from src/coffee/models/parser_versions/mod_parser_v1.coffee rename to src/client/models/parsing/mod_parser_v1.coffee index 3b6420675..f0f9ab5b8 100644 --- a/src/coffee/models/parser_versions/mod_parser_v1.coffee +++ b/src/client/models/parsing/mod_parser_v1.coffee @@ -1,14 +1,14 @@ -### -Crafting Guide - mod_parser_v2.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - mod_parser_v1.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# CommandParserVersionBase = require './command_parser_version_base' -Mod = require '../mod' -ModVersion = require '../mod_version' -Tutorial = require '../tutorial' +Mod = require '../game/mod' +ModVersion = require '../game/mod_version' +Tutorial = require '../site/tutorial' ######################################################################################################################## diff --git a/src/coffee/models/mod_version_parser.coffee b/src/client/models/parsing/mod_version_parser.coffee similarity index 71% rename from src/coffee/models/mod_version_parser.coffee rename to src/client/models/parsing/mod_version_parser.coffee index 41b3dbe07..2ba90d6c7 100644 --- a/src/coffee/models/mod_version_parser.coffee +++ b/src/client/models/parsing/mod_version_parser.coffee @@ -1,12 +1,12 @@ -### -Crafting Guide - mod_version_parser.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - mod_version_parser.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# VersionedParserBase = require './versioned_parser_base' -ModVersionParserV1 = require './parser_versions/mod_version_parser_v1' +ModVersionParserV1 = require './mod_version_parser_v1' ######################################################################################################################## diff --git a/src/coffee/models/parser_versions/mod_version_parser_v1.coffee b/src/client/models/parsing/mod_version_parser_v1.coffee similarity index 97% rename from src/coffee/models/parser_versions/mod_version_parser_v1.coffee rename to src/client/models/parsing/mod_version_parser_v1.coffee index 3896bb2dc..9248b6ad8 100644 --- a/src/coffee/models/parser_versions/mod_version_parser_v1.coffee +++ b/src/client/models/parsing/mod_version_parser_v1.coffee @@ -1,18 +1,17 @@ -### -Crafting Guide - mod_version_parser_v2.coffee +# +# Crafting Guide - mod_version_parser_v1.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' CommandParserVersionBase = require './command_parser_version_base' -Item = require '../item' -ItemSlug = require '../item_slug' -ModVersion = require '../mod_version' -Multiblock = require '../multiblock' -Recipe = require '../recipe' -Stack = require '../simple_stack' +Item = require '../game/item' +ItemSlug = require '../game/item_slug' +ModVersion = require '../game/mod_version' +Multiblock = require '../game/multiblock' +Recipe = require '../game/recipe' +Stack = require '../game/simple_stack' {StringBuilder} = require 'crafting-guide-common' ######################################################################################################################## diff --git a/test/parser_versions/mod_version_parser_v1.test.coffee b/src/client/models/parsing/mod_version_parser_v1.test.coffee similarity index 96% rename from test/parser_versions/mod_version_parser_v1.test.coffee rename to src/client/models/parsing/mod_version_parser_v1.test.coffee index 969e24cce..657f9bf60 100644 --- a/test/parser_versions/mod_version_parser_v1.test.coffee +++ b/src/client/models/parsing/mod_version_parser_v1.test.coffee @@ -1,16 +1,14 @@ -### -Crafting Guide - mod_version_parser_v1.test.coffee +# +# Crafting Guide - mod_version_parser_v1.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -CommandParserVersionBase = require '../../src/coffee/models/parser_versions/command_parser_version_base' -ItemSlug = require '../../src/coffee/models/item_slug' -ModVersion = require '../../src/coffee/models/mod_version' -ModVersionParserV1 = require '../../src/coffee/models/parser_versions/mod_version_parser_v1' -_ = require 'underscore' -{Logger} = require 'crafting-guide-common' +CommandParserVersionBase = require './command_parser_version_base' +ItemSlug = require '../game/item_slug' +ModVersion = require '../game/mod_version' +ModVersionParserV1 = require './mod_version_parser_v1' ######################################################################################################################## diff --git a/src/coffee/models/tutorial_parser.coffee b/src/client/models/parsing/tutorial_parser.coffee similarity index 71% rename from src/coffee/models/tutorial_parser.coffee rename to src/client/models/parsing/tutorial_parser.coffee index 21d83127b..40579a1aa 100644 --- a/src/coffee/models/tutorial_parser.coffee +++ b/src/client/models/parsing/tutorial_parser.coffee @@ -1,12 +1,12 @@ -### -Crafting Guide - tutorial_parser.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - tutorial_parser.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# VersionedParserBase = require './versioned_parser_base' -TutorialParserV1 = require './parser_versions/tutorial_parser_v1' +TutorialParserV1 = require './tutorial_parser_v1' ######################################################################################################################## diff --git a/src/coffee/models/parser_versions/tutorial_parser_v1.coffee b/src/client/models/parsing/tutorial_parser_v1.coffee similarity index 93% rename from src/coffee/models/parser_versions/tutorial_parser_v1.coffee rename to src/client/models/parsing/tutorial_parser_v1.coffee index c5bf37df3..a3577ee54 100644 --- a/src/coffee/models/parser_versions/tutorial_parser_v1.coffee +++ b/src/client/models/parsing/tutorial_parser_v1.coffee @@ -1,12 +1,12 @@ -### -Crafting Guide - tutorial_parser_v1.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - tutorial_parser_v1.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# CommandParserVersionBase = require './command_parser_version_base' -Tutorial = require '../tutorial' +Tutorial = require '../site/tutorial' ######################################################################################################################## diff --git a/src/coffee/models/versioned_parser_base.coffee b/src/client/models/parsing/versioned_parser_base.coffee similarity index 91% rename from src/coffee/models/versioned_parser_base.coffee rename to src/client/models/parsing/versioned_parser_base.coffee index e155f6391..6642420ad 100644 --- a/src/coffee/models/versioned_parser_base.coffee +++ b/src/client/models/parsing/versioned_parser_base.coffee @@ -1,11 +1,9 @@ -### -Crafting Guide - versioned_parser_base.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' +# +# Crafting Guide - versioned_parser_base.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# ######################################################################################################################## diff --git a/src/coffee/models/craft_page.coffee b/src/client/models/site/craft_page.coffee similarity index 67% rename from src/coffee/models/craft_page.coffee rename to src/client/models/site/craft_page.coffee index ff65749bc..106160c40 100644 --- a/src/coffee/models/craft_page.coffee +++ b/src/client/models/site/craft_page.coffee @@ -1,15 +1,14 @@ -### -Crafting Guide - craft_page.coffee +# +# Crafting Guide - craft_page.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' -Craftsman = require './crafting/craftsman' -{Event} = require '../constants' -Inventory = require './inventory' -ModPack = require './mod_pack' +BaseModel = require '../base_model' +Craftsman = require '../crafting/craftsman' +Inventory = require '../game/inventory' +ModPack = require '../game/mod_pack' ######################################################################################################################## @@ -21,10 +20,10 @@ module.exports = class CraftPage extends BaseModel attributes.craftsman ?= new Craftsman attributes.modPack super attributes, options - @modPack.on Event.change, => @_consumeParams() - @on Event.change + ':params', => @_consumeParams() - @craftsman.on Event.change + ':stage', => @trigger Event.change, this - @craftsman.on Event.change + ':complete', => @trigger Event.change, this + @modPack.on c.event.change, => @_consumeParams() + @on c.event.change + ':params', => @_consumeParams() + @craftsman.on c.event.change + ':stage', => @trigger c.event.change, this + @craftsman.on c.event.change + ':complete', => @trigger c.event.change, this # Private Methods ############################################################################## diff --git a/src/coffee/models/editable_file.coffee b/src/client/models/site/editable_file.coffee similarity index 62% rename from src/coffee/models/editable_file.coffee rename to src/client/models/site/editable_file.coffee index 033ead12d..b37bda8b5 100644 --- a/src/coffee/models/editable_file.coffee +++ b/src/client/models/site/editable_file.coffee @@ -1,19 +1,17 @@ -### -Crafting Guide - editable_file.coffee +# +# Crafting Guide - editable_file.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' -{Event} = require '../constants' -w = require 'when' +BaseModel = require '../base_model' ######################################################################################################################## module.exports = class EditableFile extends BaseModel - @MimeTypes = MimeTypes = [ + @::MimeTypes = [ { pattern:/\.cg$/i, text:'text/plain' } { pattern:/\.png$/i, text:'image/png' } { pattern:/\.gif$/i, text:'image/gif' } @@ -21,7 +19,7 @@ module.exports = class EditableFile extends BaseModel { pattern:/\.jpeg$/i, text:'image/jpeg' } ] - @Status = Status = { + @::Status = { 'unknown': 'unknown' 'checking': 'checking' 'empty': 'empty' @@ -30,16 +28,17 @@ module.exports = class EditableFile extends BaseModel } constructor: (attributes={}, options={})-> + if not options.client? then throw new Error 'options.client is required' attributes.fileName ?= '' attributes.path ?= '' attributes.sha ?= null - attributes.status ?= Status.unknown - super + super attributes, options - @client = options.client + @_client = options.client + @_status = @Status.unknown @_encodedData = null - @on Event.change + ':fileName', => @_mimeType = null + @on c.event.change + ':fileName', => @_mimeType = null # Public Methods ############################################################################### @@ -66,66 +65,79 @@ module.exports = class EditableFile extends BaseModel @_encodedData = newEncodedData @_updateStatusForNewData() - @trigger Event.change + ':encodedData', this, oldEncodedData, newEncodedData - @trigger Event.change, this + @trigger c.event.change + ':encodedData', this, oldEncodedData, newEncodedData + @trigger c.event.change, this getFullPath: -> return "#{@path}/#{@fileName}" getMimeType: -> if not @_mimeType? - for mimeType in MimeTypes + for mimeType in @MimeTypes if mimeType.pattern.test @fileName @_mimeType = mimeType.text break return @_mimeType + getStatus: -> + return @_status + isValid: -> - return @status in [ Status.clean, Status.dirty ] + return @_status in [ @Status.clean, @Status.dirty ] Object.defineProperties @prototype, encodedData: { get:@prototype.getEncodedData, set:@prototype.setEncodedData } fullPath: { get:@prototype.getFullPath } imageUrl: { get:@prototype.getImageUrl } mimeType: { get:@prototype.getMimeType } + status: { get:@prototype.getStatus } valid: { get:@prototype.isValid } # BaseModel Overrides ########################################################################## fetch: -> - if not @client? then throw new Error 'EditableFile must be given a client to fetch with' + if not @_client? then throw new Error 'EditableFile must be given a client to fetch with' - @status = Status.checking - @client.fetchFile path:@fullPath + @_updateStatus @Status.checking + @_client.fetchFile path:@fullPath .then (response)=> data = response.json.data if data.sha? @encodedData = data.content @sha = data.sha + @_updateStatusForNewData() else - @status = Status.empty + @_updateStatus @Status.empty return this save: (commitMessage)-> - return w(true) if @status is Status.clean + return w(true) if @_status is @Status.clean return w(true) unless @encodedData? - if not @valid then return w.reject new Error "cannot save with an invalid status: #{@status}" + if not @valid then return w.reject new Error "cannot save with an invalid status: #{@_status}" commitMessage ?= "User-submitted update to #{@fileName} from #{global.hostName}" - @client.updateFile content:@encodedData, message:commitMessage, path:@fullPath, sha:@sha + @_client.updateFile content:@encodedData, message:commitMessage, path:@fullPath, sha:@sha # Private Methods ############################################################################## + _updateStatus: (newStatus)-> + oldStatus = @_status + return if oldStatus is newStatus + + @_status = newStatus + @trigger c.event.change, this, oldStatus, newStatus + @trigger c.event.change, this + _updateStatusForNewData: -> - switch @status - when Status.unknown - @status = Status.dirty - when Status.checking - @status = Status.clean - when Status.empty - @status = Status.dirty - when Status.clean - @status = Status.dirty + switch @_status + when @Status.unknown + @_updateStatus @Status.dirty + when @Status.checking + @_updateStatus @Status.clean + when @Status.empty + @_updateStatus @Status.dirty + when @Status.clean + @_updateStatus @Status.dirty diff --git a/src/client/models/site/email_client.coffee b/src/client/models/site/email_client.coffee new file mode 100644 index 000000000..f8a17c889 --- /dev/null +++ b/src/client/models/site/email_client.coffee @@ -0,0 +1,32 @@ +# +# Crafting Guide - email_client.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +emailjs = require 'emailjs' + +######################################################################################################################## + +emailjs.init 'user_sLxEH6RwPvzowjaIkfY6H' + +######################################################################################################################## + +module.exports = class EmailClient + + constructor: -> + @serviceId = 'default_service' + + # Public Methods ############################################################################### + + send: (template, data={})-> + logger.info -> "sending email with template #{template} and data: #{JSON.stringify(data)}" + + emailjs.send @serviceId, template, data + .then (response)-> + logger.info -> "Email sent! status: #{response.status}, message: #{response.text}" + return status:response.status, message:response.text + .catch (error)-> + logger.error -> "Email failed! error: #{error}" + throw error diff --git a/src/coffee/models/user.coffee b/src/client/models/site/github_user.coffee similarity index 78% rename from src/coffee/models/user.coffee rename to src/client/models/site/github_user.coffee index 0d085bc2e..fb2afe354 100644 --- a/src/coffee/models/user.coffee +++ b/src/client/models/site/github_user.coffee @@ -1,19 +1,18 @@ -### -Crafting Guide - user.coffee +# +# Crafting Guide - github_user.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' -{Url} = require '../constants' +BaseModel = require '../base_model' ######################################################################################################################## module.exports = class GitHubUser extends BaseModel constructor: (attributes={}, options={})-> - attributes.avatarUrl ?= null + attributes.avatarUrl ?= attributes.avatar_url ?= null attributes.email ?= null attributes.login ?= null attributes.name ?= null diff --git a/src/coffee/models/item_page.coffee b/src/client/models/site/item_page.coffee similarity index 83% rename from src/coffee/models/item_page.coffee rename to src/client/models/site/item_page.coffee index b8b51d951..94ca571ed 100644 --- a/src/coffee/models/item_page.coffee +++ b/src/client/models/site/item_page.coffee @@ -1,14 +1,11 @@ -### -Crafting Guide - item_page.coffee +# +# Crafting Guide - item_page.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' -BaseModel = require './base_model' -{Event} = require '../constants' -{Url} = require '../constants' +BaseModel = require '../base_model' ######################################################################################################################## @@ -42,13 +39,13 @@ module.exports = class ItemPage extends BaseModel # Private Methods ############################################################################## - _findRecipesMatching: (callback)-> + _findRecipesMatching: (isAcceptable)-> return null unless @item? result = {} @modPack.eachMod (mod)=> mod.eachRecipe (recipe)=> - if callback(recipe) + if isAcceptable recipe for outputStack in recipe.output outputItem = @modPack.findItem outputStack.itemSlug, includeDisabled:true result[outputItem.slug] = outputItem diff --git a/src/coffee/models/item_selector.coffee b/src/client/models/site/item_selector.coffee similarity index 74% rename from src/coffee/models/item_selector.coffee rename to src/client/models/site/item_selector.coffee index 6cf85a8e5..ae6ec3071 100644 --- a/src/coffee/models/item_selector.coffee +++ b/src/client/models/site/item_selector.coffee @@ -1,13 +1,12 @@ -### -Crafting Guide - item_selector.coffee +# +# Crafting Guide - item_selector.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' -ItemSlug = require './item_slug' -_ = require 'underscore' +BaseModel = require '../base_model' +ItemSlug = require '../game/item_slug' ######################################################################################################################## @@ -26,25 +25,25 @@ module.exports = class ItemSelector extends BaseModel # Property Methods ############################################################################# - getHint: -> - return @_hint - - setHint: (newHint)-> - oldHint = @_hint - return if newHint is oldHint - - @_hint = newHint.toLowerCase() - - @trigger Event.change + ':hint', this, oldHint, newHint - @_refreshResults() - @trigger Event.change, this - - getResults: -> - return @_results - Object.defineProperties @prototype, - hint: {get:@prototype.getHint, set:@prototype.setHint} - results: {get:@prototype.getResults} + + hint: + get: -> + return @_hint + + set: (newHint)-> + oldHint = @_hint + return if newHint is oldHint + + @_hint = newHint.toLowerCase() + + @trigger c.event.change + ':hint', this, oldHint, newHint + @_refreshResults() + @trigger c.event.change, this + + results: + get: -> + return @_results # Private Methods ############################################################################## @@ -87,4 +86,4 @@ module.exports = class ItemSelector extends BaseModel newResults.sort ItemSlug.compare @_results = newResults - @trigger Event.change + ':results', this, oldResults, newResults + @trigger c.event.change + ':results', this, oldResults, newResults diff --git a/src/coffee/models/markdown_image.coffee b/src/client/models/site/markdown_image.coffee similarity index 80% rename from src/coffee/models/markdown_image.coffee rename to src/client/models/site/markdown_image.coffee index 27817d2b0..0860d7a21 100644 --- a/src/coffee/models/markdown_image.coffee +++ b/src/client/models/site/markdown_image.coffee @@ -1,11 +1,10 @@ -### -Crafting Guide - markdown_image.coffee +# +# Crafting Guide - markdown_image.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' EditableFile = require './editable_file' ######################################################################################################################## diff --git a/src/coffee/models/markdown_image_list.coffee b/src/client/models/site/markdown_image_list.coffee similarity index 79% rename from src/coffee/models/markdown_image_list.coffee rename to src/client/models/site/markdown_image_list.coffee index 4f7aa9e9f..9ad3331e3 100644 --- a/src/coffee/models/markdown_image_list.coffee +++ b/src/client/models/site/markdown_image_list.coffee @@ -1,12 +1,11 @@ -### -Crafting Guide - markdown_image_list.coffee +# +# Crafting Guide - markdown_image_list.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' -{Event} = require '../constants' +BaseModel = require '../base_model' MarkdownImage = require './markdown_image' ######################################################################################################################## @@ -21,11 +20,11 @@ module.exports = class MarkdownImageList extends BaseModel @client = options.client @_images = {} - @on Event.change + ':imageBase', => + @on c.event.change + ':imageBase', => for fileName, image of @_images image.path = @imageBase - @on Event.change + ':markdownText', => @_analyzeMarkdownText() + @on c.event.change + ':markdownText', => @_analyzeMarkdownText() @_analyzeMarkdownText() # Public Methods ############################################################################### @@ -35,7 +34,7 @@ module.exports = class MarkdownImageList extends BaseModel fetchImages: -> for fileName, image of @_images - if image.status is MarkdownImage.Status.unknown + if image.status is MarkdownImage::Status.unknown image.fetch() reset: -> @@ -80,17 +79,17 @@ module.exports = class MarkdownImageList extends BaseModel image = @_images[fileName] if not image? image = new MarkdownImage {fileName:fileName, path:@imageBase}, {client:@client} - @listenTo image, Event.change, => @trigger Event.change, this - @trigger Event.add, this, image + @listenTo image, c.event.change, => @trigger c.event.change, this + @trigger c.event.add, this, image changed = true newImages[fileName] = image for fileName, image of @_images if not newImages[fileName]? - @trigger Event.remove, this, image + @trigger c.event.remove, this, image changed = true if changed @_images = newImages - @trigger Event.change, this + @trigger c.event.change, this diff --git a/test/markdown_image_list.test.coffee b/src/client/models/site/markdown_image_list.test.coffee similarity index 93% rename from test/markdown_image_list.test.coffee rename to src/client/models/site/markdown_image_list.test.coffee index 871f98e5c..ed31a6dad 100644 --- a/test/markdown_image_list.test.coffee +++ b/src/client/models/site/markdown_image_list.test.coffee @@ -1,11 +1,11 @@ -### -Crafting Guide - markdown_image_list_test.coffee +# +# Crafting Guide - markdown_image_list.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -MarkdownImageList = require '../src/coffee/models/markdown_image_list' +MarkdownImageList = require './markdown_image_list' ######################################################################################################################## diff --git a/src/coffee/models/tutorial.coffee b/src/client/models/site/tutorial.coffee similarity index 66% rename from src/coffee/models/tutorial.coffee rename to src/client/models/site/tutorial.coffee index ece68b59b..702f0d718 100644 --- a/src/coffee/models/tutorial.coffee +++ b/src/client/models/site/tutorial.coffee @@ -1,14 +1,11 @@ -### -Crafting Guide - tutorial.coffee +# +# Crafting Guide - tutorial.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseModel = require './base_model' -TutorialParser = require './tutorial_parser' -_ = require 'underscore' -{Url} = require '../constants' +BaseModel = require '../base_model' ######################################################################################################################## @@ -26,11 +23,11 @@ module.exports = class Tutorial extends BaseModel # Backbone.Model Overrides ##################################################################### parse: (text)-> - TutorialParser = require './tutorial_parser' # to avoid require cycles + TutorialParser = require '../parsing/tutorial_parser' # to avoid require cycles @_parser ?= new TutorialParser model:this @_parser.parse text return null # prevent calling `set` url: -> - return Url.tutorialData modSlug:@modSlug, tutorialSlug:@slug + return c.url.tutorialData modSlug:@modSlug, tutorialSlug:@slug diff --git a/src/client/site/base_controller.coffee b/src/client/site/base_controller.coffee new file mode 100644 index 000000000..1981c7e38 --- /dev/null +++ b/src/client/site/base_controller.coffee @@ -0,0 +1,162 @@ +# +# Crafting Guide - base_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +templates = require './templates' + +######################################################################################################################## + +module.exports = class BaseController extends Backbone.View + + constructor: (options={})-> + @_children = [] + @_model = null + @_parent = options.parent + @_rendered = false + + @router = options.router + + @tryRefresh = _.debounce (=> @_tryRefresh()), 100 + + @_loadTemplate options.templateName + super options + + # Public Methods ############################################################################### + + addChild: (Controller, atSelector, options={})-> + if not _.isFunction Controller then throw new Error "Controller must be a constructor" + + options.el = @$(atSelector)[0] + options.parent = this + + child = new Controller options + child.render options + @_children.push child + return child + + hide: ($el)-> + $el ?= @$el + $el.css 'display', 'none' + + refresh: -> + logger.verbose => "#{this} refreshing" + + remove: -> + @$el.remove() + @off() + + routeLinkClick: (event)-> + event.preventDefault() + href = $(event.target).attr 'href' + href ?= $(event.currentTarget).attr 'href' + logger.info "Re-routing link to internal navigation: #{href}" + + if href? and href.match /^http/ + window.location.href = href + else + @router.navigate href, trigger:true + + show: ($el)-> + $el ?= @$el + $el.css 'display', '' + + unrender: -> + @undelegateEvents() + @$el.empty() + @_rendered = false + + # Event Methods ################################################################################ + + onDidModelChange: -> + @tryRefresh() + + onDidModelSync: -> + @tryRefresh() + + onWillRender: -> # do nothing + + onDidRender: -> # do nothing + + onWillShow: -> # do nothing + + onDidShow: -> # do nothing + + onWillChangeModel: (oldModel, newModel)-> + if oldModel?.on? + @stopListening oldModel + if newModel?.on? + @listenTo newModel, 'sync', (e)=> @onDidModelSync e + @listenTo newModel, 'change', (e)=> @onDidModelChange e + return newModel + + # Property Methods ############################################################################# + + Object.defineProperties @prototype, + model: + get: -> @_model + set: (newModel)-> + return if @model is newModel + + newModel = @onWillChangeModel @_model, newModel + @_model = newModel + @tryRefresh() + + rendered: + get: -> @_rendered + + user: + get: -> @_user + set: (newUser)-> + @_user = newUser + @tryRefresh() + + # Backbone.View Overrides ###################################################################### + + events: -> + return {} + + render: (options={})-> + options.force ?= false + options.show ?= true + return this unless not @_rendered or options.force + + if not @_template? + logger.error => "Default render called for #{@constructor.name} without a template" + return this + + data = (@model?.toHash? and @model.toHash()) or @model or {} + logger.verbose => "#{this} rendering with data: #{data}" + $renderedEl = $($(@_template(data))[0]) + + @onWillRender() + @unrender() + + @$el.append $renderedEl.children() + @$el.addClass $renderedEl.attr 'class' + @$el.data $renderedEl.data() + @delegateEvents() + + @_rendered = true + @onDidRender() + + @refresh() + + return this + + # Object Overrides ############################################################################# + + toString: -> + return "#{@constructor.name}.#{@cid}" + + # Private Methods ############################################################################## + + _loadTemplate: (templateName)-> + if templateName? + @_template = templates[templateName] + + _tryRefresh: -> + return unless @_rendered + @refresh() diff --git a/src/client/site/browse_page/browse_page.jade b/src/client/site/browse_page/browse_page.jade new file mode 100644 index 000000000..c2d31a403 --- /dev/null +++ b/src/client/site/browse_page/browse_page.jade @@ -0,0 +1,13 @@ +//- +//- Crafting Guide - browse_page.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.content.view__browse_page + .left + .view__adsense + + .right + .tile_container \ No newline at end of file diff --git a/src/client/site/browse_page/browse_page.scss b/src/client/site/browse_page/browse_page.scss new file mode 100644 index 000000000..fd09fa47f --- /dev/null +++ b/src/client/site/browse_page/browse_page.scss @@ -0,0 +1,23 @@ +// +// Crafting Guide - browse_page.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__browse_page { + @include layout-body-with-sidebar; + + .right { + .tile_container { + display : flex; + flex-wrap : wrap; + justify-content : space-between; + + .view__mod_tile { + max-width : calc(50% - 12px); // $size-margin-large / 2 + margin-bottom : $size-margin-large; + } + } + } +} diff --git a/src/client/site/browse_page/browse_page_controller.coffee b/src/client/site/browse_page/browse_page_controller.coffee new file mode 100644 index 000000000..7791c7c44 --- /dev/null +++ b/src/client/site/browse_page/browse_page_controller.coffee @@ -0,0 +1,64 @@ +# +# Crafting Guide - browse_page_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +AdsenseController = require '../common/adsense/adsense_controller' +ModTileController = require './mod_tile/mod_tile_controller' +PageController = require '../page_controller' + +######################################################################################################################## + +module.exports = class BrowsePageController extends PageController + + constructor: (options={})-> + if not options.modPack then throw new Error 'options.modPack is required' + options.templateName = 'browse_page' + super options + + @_modPack = options.modPack + @_tileControllers = [] + + # PageController Overrides ##################################################################### + + getTitle: -> + return "Browse" + + # BaseController Overrides ##################################################################### + + onDidRender: -> + @_adsenseController = @addChild AdsenseController, '.view__adsense', model:'skyscraper' + + @$tileContainer = @$('.tile_container') + + refresh: -> + @_refreshModTiles() + super + + # Backbone.View Overrides ###################################################################### + + events: -> + return _.extend super, + 'click a': 'routeLinkClick' + + # Private Methods ############################################################################## + + _refreshModTiles: -> + index = 0 + mods = @_modPack.getAllMods() + for mod in mods + controller = @_tileControllers[index] + if not controller + controller = new ModTileController model:mod, router:@router + controller.render() + @$tileContainer.append controller.$el + @_tileControllers.push controller + else + controller.model = mod + index++ + + while @_tileControllers.length > mods.length + controller = @_tileControllers.pop() + controller.remove() diff --git a/src/client/site/browse_page/mod_tile/mod_tile.jade b/src/client/site/browse_page/mod_tile/mod_tile.jade new file mode 100644 index 000000000..aa0138d6a --- /dev/null +++ b/src/client/site/browse_page/mod_tile/mod_tile.jade @@ -0,0 +1,14 @@ +//- +//- Crafting Guide - mod_tile.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__mod_tile + a + .left + img + .right + p.title + p.description diff --git a/src/client/site/browse_page/mod_tile/mod_tile.scss b/src/client/site/browse_page/mod_tile/mod_tile.scss new file mode 100644 index 000000000..85e5ec908 --- /dev/null +++ b/src/client/site/browse_page/mod_tile/mod_tile.scss @@ -0,0 +1,88 @@ +// +// Crafting Guide - mod_tile.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__mod_tile { + min-width : $size-minecraft-block * 9; + + display : flex; + justify-content : stretch; + align-items : stretch; + + a { + max-width: 100%; + + @include floating-panel; + border : $size-border-medium solid $color-background-panel; + color : $color-text; + text-decoration : none; + + display : flex; + padding : $size-margin-medium; + + & > .left { + flex: 0 0 $size-minecraft-block * 4; + margin-right: $size-margin-medium; + + img { + width: $size-minecraft-block * 4; + max-height: $size-minecraft-block * 4; + } + } + + & > .right { + flex : 1 1 100%; + + overflow : hidden; + + .title { + margin-bottom : $size-margin-medium; + + font-family : $font-family-header; + font-size : $font-size-xlarge; + } + + .description { + font-family : $font-family-text; + font-size : $font-size-medium; + line-height : $font-size-medium * 1.5; + } + } + + &:hover { + background: $color-blue-faint; + border-color: $color-link-normal; + + & > .right { + .title { + color: $color-link-normal; + text-decoration: underline; + } + } + } + } + + &.disabled { + a { + & > .left { + img { + @include grayscale; + opacity: 0.25; + } + } + + & > .right { + .title { + color: $color-gray-light; + } + + .description { + color: $color-gray-light; + } + } + } + } +} diff --git a/src/client/site/browse_page/mod_tile/mod_tile_controller.coffee b/src/client/site/browse_page/mod_tile/mod_tile_controller.coffee new file mode 100644 index 000000000..049e494f0 --- /dev/null +++ b/src/client/site/browse_page/mod_tile/mod_tile_controller.coffee @@ -0,0 +1,44 @@ +# +# Crafting Guide - mod_tile_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +BaseController = require '../../base_controller' + +######################################################################################################################## + +module.exports = class ModTileController extends BaseController + + constructor: (options={})-> + options.templateName = 'browse_page/mod_tile' + super options + + # BaseController Overrides ##################################################################### + + onDidRender: -> + @$link = @$('a') + @$logoImage = @$('img') + @$title = @$('p.title') + @$description = @$('p.description') + super + + refresh: -> + @$link.attr 'href', c.url.mod modSlug:@model.slug + @$logoImage.attr 'src', c.url.modIcon modSlug:@model.slug + @$title.text @model.name + @$description.text @model.description + + if @model.enabled + @$el.removeClass 'disabled' + else + @$el.addClass 'disabled' + + super + + # Backbone.View Overrides ###################################################################### + + events: -> + _.extend super, + 'click a': 'routeLinkClick' diff --git a/src/client/site/common/adsense/adsense.jade b/src/client/site/common/adsense/adsense.jade new file mode 100644 index 000000000..e9de92cb9 --- /dev/null +++ b/src/client/site/common/adsense/adsense.jade @@ -0,0 +1,8 @@ +//- +//- Crafting Guide - adsense.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__adsense diff --git a/src/client/site/common/adsense/adsense.scss b/src/client/site/common/adsense/adsense.scss new file mode 100644 index 000000000..5ac154fc8 --- /dev/null +++ b/src/client/site/common/adsense/adsense.scss @@ -0,0 +1,25 @@ +// +// Crafting Guide - adsense.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__adsense { + .skyscraper { + height : $size-skyscraper-height; + width : $size-skyscraper-width; + position : relative; + + border : 0.1em solid $color-gray-faint; + margin : $size-margin-large 0; + + &:first-child { + margin-top : 0; + } + + ins { + position: absolute; top: 0; right: 0; bottom: 0; left: 0; + } + } +} diff --git a/src/coffee/controllers/adsense_controller.coffee b/src/client/site/common/adsense/adsense_controller.coffee similarity index 54% rename from src/coffee/controllers/adsense_controller.coffee rename to src/client/site/common/adsense/adsense_controller.coffee index b298cf0ab..4671f0e44 100644 --- a/src/coffee/controllers/adsense_controller.coffee +++ b/src/client/site/common/adsense/adsense_controller.coffee @@ -1,46 +1,39 @@ -### -Crafting Guide - adsense_controller.coffee +# +# Crafting Guide - adsense_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' -BaseController = require './base_controller' -_ = require 'underscore' -{Adsense} = require '../constants' -{Duration} = require '../constants' -{ProductionEnvs} = require '../constants' +BaseController = require '../../base_controller' ######################################################################################################################## module.exports = class AdsenseController extends BaseController constructor: (options={})-> - options.templateName = "adsense_sidebar_skyscraper" + options.templateName = 'common/adsense' super options - @_adsEnabled = global.env in ProductionEnvs - @_adHeight = 630 - @_adCount = 0 - @_waiting = false + @_adsEnabled = global.env in c.productionEnvs + @_adCount = 0 + @_waiting = false # Public Methods ############################################################################### fillAdPositions: -> if @_adCount > 0 - return unless @_adCount < Adsense.slotIds.length - return unless @$sidebar? and @$mainBody? - return unless @$sidebar.height() + @_adHeight < @$mainBody.height() + return unless @$sidebar and @$mainBody + return unless @_adCount < @_computeMaxAds() + return unless @_adCount < c.adsense.slotIds.length - $adContainer = $('') + $adContainer = $('
') @$el.append $adContainer if @_adsEnabled $ad = $('') - $ad.attr 'data-ad-client', Adsense.clientId - $ad.attr 'data-ad-slot', Adsense.slotIds[@_adCount] - $ad.css 'height':'600px', 'width':'160px' + $ad.attr 'data-ad-client', c.adsense.clientId + $ad.attr 'data-ad-slot', c.adsense.slotIds[@_adCount] $adContainer.append $ad @_loadAds() @@ -50,8 +43,8 @@ module.exports = class AdsenseController extends BaseController # BaseController Overrides ##################################################################### onDidRender: -> - @$mainBody = $('.mainBody') - @$sidebar = $('.sidebar') + @$mainBody = $('.page > .content > .right') + @$sidebar = $('.page > .content > .left') super refresh: -> @@ -60,6 +53,11 @@ module.exports = class AdsenseController extends BaseController # Private Methods ############################################################################# + _computeMaxAds: -> + return null unless @$sidebar + result = Math.floor @$sidebar.height() / (c.adsense.skyscraper.height + c.adsense.skyscraper.margin) + return result + _loadAds: -> return unless @_adsEnabled @@ -73,8 +71,10 @@ module.exports = class AdsenseController extends BaseController _waitForPageReadiness: -> return if @_waiting - if @$mainBody.height() < @_adHeight / 2 + if @$sidebar.height() < c.adsense[@model].height / 2 + logger.verbose "Adsense is waiting for room to insert ads" @_waiting = true - _.delay (=> @_waiting = false; @_waitForPageReadiness()), Duration.normal + _.delay (=> @_waiting = false; @_waitForPageReadiness()), c.duration.normal else + logger.verbose "Adsense is ready to fill ads" @fillAdPositions() diff --git a/src/client/site/common/crafting_grid/crafting_grid.jade b/src/client/site/common/crafting_grid/crafting_grid.jade new file mode 100644 index 000000000..c2ee681e7 --- /dev/null +++ b/src/client/site/common/crafting_grid/crafting_grid.jade @@ -0,0 +1,20 @@ +//- +//- Crafting Guide - crafting_grid.jade +//- +//- Copyright (c) 2015 by Redwood Labs +//- All rights reserved. +//- + +.view__crafting_grid + .row + .view__slot + .view__slot + .view__slot + .row + .view__slot + .view__slot + .view__slot + .row + .view__slot + .view__slot + .view__slot diff --git a/src/client/site/common/crafting_grid/crafting_grid.scss b/src/client/site/common/crafting_grid/crafting_grid.scss new file mode 100644 index 000000000..67d36fb5c --- /dev/null +++ b/src/client/site/common/crafting_grid/crafting_grid.scss @@ -0,0 +1,27 @@ +// +// Crafting Guide - crafting_grid.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__crafting_grid { + background : $color-gray-light; + border : $size-border-medium solid $color-gray-medium; + + display : flex; + flex-direction : column; + + .row { + flex: 1 1 auto; + + display: flex; + + .view__slot { + flex: 1 1 auto; + + background : $color-white; + margin : $size-border-small; + } + } +} diff --git a/src/client/site/common/crafting_grid/crafting_grid_controller.coffee b/src/client/site/common/crafting_grid/crafting_grid_controller.coffee new file mode 100644 index 000000000..48c2a2edc --- /dev/null +++ b/src/client/site/common/crafting_grid/crafting_grid_controller.coffee @@ -0,0 +1,43 @@ +# +# Crafting Guide - crafting_grid_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +BaseController = require '../../base_controller' +SlotController = require '../slot/slot_controller' + +######################################################################################################################## + +module.exports = class CraftingGridController extends BaseController + + constructor: (options={})-> + if not options.imageLoader? then throw new Error 'options.imageLoader is required' + if not options.modPack? then throw new Error 'options.modPack is required' + if not options.router? then throw new Error 'options.router is required' + # options.model should be a recipe + options.templateName = 'common/crafting_grid' + super options + + @_imageLoader = options.imageLoader + @_modPack = options.modPack + @_router = options.router + + @_modPack.on c.event.change, => @tryRefresh() + + # BaseController Methods ####################################################################### + + onDidRender: -> + @_slotControllers = [] + for el in @$('.view__slot') + controller = new SlotController el:el, imageLoader:@_imageLoader, modPack:@_modPack, router:@_router + controller.render() + @_slotControllers.push controller + super + + refresh: -> + for controller, index in @_slotControllers + controller.model = @model?.getStackAtSlot(index) + + super diff --git a/src/client/site/common/inventory/inventory.jade b/src/client/site/common/inventory/inventory.jade new file mode 100644 index 000000000..48df8182d --- /dev/null +++ b/src/client/site/common/inventory/inventory.jade @@ -0,0 +1,13 @@ +//- +//- Crafting Guide - inventory.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__inventory + .item_container + .empty_placeholder nothing + .buttons + .button.item-selector: .bezel: p add an item... + .button.clear: .bezel: p clear diff --git a/src/client/site/common/inventory/inventory.scss b/src/client/site/common/inventory/inventory.scss new file mode 100644 index 000000000..d8778b64a --- /dev/null +++ b/src/client/site/common/inventory/inventory.scss @@ -0,0 +1,93 @@ +// +// Crafting Guide - inventory.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__inventory { + display : flex; + flex-direction : column; + + .empty_placeholder { + color : $color-gray-light; + font-family : $font-family-text; + font-size : $font-size-large; + margin : $size-margin-large 0; + text-align : center; + } + + .item_container { + flex: 0 1 100%; + + display: table; + } + + .buttons { + display: none; + } +} + +// Editable Variant //////////////////////////////////////////////////////////////////////////////////////////////////// + +.view__inventory.editable { + .buttons { + display : flex; + flex-direction : row; + + margin-top: $size-margin-large; + + .item-selector { + flex : 85%; + margin-right : $size-margin-medium; + } + + .clear { + flex : 15%; + } + } +} + +// Large variant /////////////////////////////////////////////////////////////////////////////////////////////////////// + +.view__inventory.large { + .view__stack { + & > * { + &:not(:last-child) { + padding-bottom : $size-margin-small; + } + } + + .quantity { + padding-right : $size-margin-medium; + input { + width: 3em; + font-size : $font-size-xlarge; + } + } + + .icon { + padding-right : $size-margin-medium; + + img { + height : $size-minecraft-block * 1.5; + width : $size-minecraft-block * 1.5; + } + } + + .name { + a { + font-family : $font-family-text; + font-size : $font-size-xlarge; + } + } + + .action { + padding-left : $size-margin-small; + + .button { + width : $size-button-height; + } + } + } +} diff --git a/src/client/site/common/inventory/inventory_controller.coffee b/src/client/site/common/inventory/inventory_controller.coffee new file mode 100644 index 000000000..8d86f3aba --- /dev/null +++ b/src/client/site/common/inventory/inventory_controller.coffee @@ -0,0 +1,151 @@ +# +# Crafting Guide - inventory_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +BaseController = require '../../base_controller' +ItemSelectorController = require '../item_selector/item_selector_controller' +StackController = require '../stack/stack_controller' + +######################################################################################################################## + +### +Events: + clear(this) + change(this) + add(this, itemSlug) + button:first(this, itemSlug) + button:second(this, itemSlug) +### +module.exports = class InventoryController extends BaseController + + @MAX_QUANTITY = 9999 + + @ONLY_DIGITS = /^[0-9]*$/ + + constructor: (options={})-> + if not options.imageLoader? then throw new Error 'options.imageLoader is required' + if not options.modPack? then throw new Error 'options.modPack is required' + if not options.router? then throw new Error 'options.router is required' + + @_imageLoader = options.imageLoader + @_modPack = options.modPack + @_router = options.router + + @_editable = options.editable ?= true + @_icon = options.icon ?= '/images/chest_front.png' + @_firstButtonType = options.firstButtonType ?= null + @_isAcceptable = options.isAcceptable ?= null + @_secondButtonType = options.secondButtonType ?= null + @_shouldEnableButton = options.shouldEnableButton ?= (model, button)-> true + + options.templateName = 'common/inventory' + super options + + @_stackControllers = [] + + @listenTo @_modPack, c.event.change, => @tryRefresh() + + # Event Methods ################################################################################ + + onClearButtonClicked: -> + return unless @model? + return if @$clearButton.hasClass 'disabled' + + @model.clear() + @trigger c.event.clear, this + @trigger c.event.change, this + + onFirstButtonClicked: (stackController)-> + @trigger c.event.button.first, this, stackController?.model?.itemSlug + + onItemSelectorButtonClicked: -> + return unless @model? + + @_selector.launch() + .then (itemSlug)=> + return unless itemSlug? + + @model.add itemSlug, 1 + @trigger c.event.add, this, itemSlug + @trigger c.event.change, this + + onSecondButtonClicked: (stackController)-> + @trigger c.event.button.second, this, stackController?.model?.itemSlug + + # BaseController Overrides ##################################################################### + + onDidRender: -> + @_selector = @addChild ItemSelectorController, null, isAcceptable: @_isAcceptable, modPack: @_modPack + + @$clearButton = @$('.button.clear') + @$emptyPlaceholder = @$('.empty_placeholder') + @$icon = @$('.icon') + @$itemContainer = @$('.item_container') + @$title = @$('h2 p') + super + + refresh: -> + if @_editable + @_selector.show() + @show @$clearButton + else + @_selector.hide() + @hide @$clearButton + + @$icon.attr 'src', @_icon + + @_refreshStacks() + + if not @model or @model.isEmpty + @show @$emptyPlaceholder + @$clearButton.addClass 'disabled' + else + @hide @$emptyPlaceholder + @$clearButton.removeClass 'disabled' + + super + + # Backbone.View Overrides ###################################################################### + + events: -> + return _.extend super, + 'click .button.item-selector': 'onItemSelectorButtonClicked' + 'click .button.clear': 'onClearButtonClicked' + 'click button.first': 'onFirstButtonClicked' + 'click button.second': 'onSecondButtonClicked' + + # Private Methods ############################################################################## + + _refreshStacks: -> + @_stackControllers ?= [] + index = 0 + + if @model? + @model.each (stack)=> + controller = @_stackControllers[index] + if not controller? + controller = new StackController + editable: @_editable + firstButtonType: @_firstButtonType + imageLoader: @_imageLoader + model: stack + modPack: @_modPack + router: @_router + secondButtonType: @_secondButtonType + shouldEnableButton: @_shouldEnableButton + controller.on c.event.change, => @trigger c.event.change, this + controller.on c.event.button.first, (c)=> @onFirstButtonClicked(c) + controller.on c.event.button.second, (c)=> @onSecondButtonClicked(c) + controller.render() + + @_stackControllers.push controller + @$itemContainer.append controller.$el + else + controller.model = stack + index += 1 + + while @_stackControllers.length > index + @_stackControllers.pop().remove() diff --git a/src/jade/templates/item_group.jade b/src/client/site/common/item_group/item_group.jade similarity index 75% rename from src/jade/templates/item_group.jade rename to src/client/site/common/item_group/item_group.jade index f8cf6d549..d6983232c 100644 --- a/src/jade/templates/item_group.jade +++ b/src/client/site/common/item_group/item_group.jade @@ -5,6 +5,6 @@ //- All rights reserved. //- -.view__item_group.section.hideable.hidden +section.view__item_group h2 .panel diff --git a/src/client/site/common/item_group/item_group.scss b/src/client/site/common/item_group/item_group.scss new file mode 100644 index 000000000..c05403e37 --- /dev/null +++ b/src/client/site/common/item_group/item_group.scss @@ -0,0 +1,19 @@ +// +// Crafting Guide - item_group.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__item_group { + .panel { + display : flex; + flex-wrap : wrap; + justify-content : space-between; + + .view__item_tile { + margin-bottom: $size-margin-medium; + width: calc(33% - 8px); // $size-margin-xsmall * 2 + } + } +} diff --git a/src/coffee/controllers/item_group_controller.coffee b/src/client/site/common/item_group/item_group_controller.coffee similarity index 65% rename from src/coffee/controllers/item_group_controller.coffee rename to src/client/site/common/item_group/item_group_controller.coffee index be11c7238..358cc6e89 100644 --- a/src/coffee/controllers/item_group_controller.coffee +++ b/src/client/site/common/item_group/item_group_controller.coffee @@ -1,15 +1,12 @@ -### -Crafting Guide - item_group_controller.coffee +# +# Crafting Guide - item_group_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -Item = require '../models/item' -ItemController = require './item_controller' -{Duration} = require '../constants' -{Event} = require '../constants' +BaseController = require '../../base_controller' +ItemController = require './item_tile/item_tile_controller' ######################################################################################################################## @@ -18,26 +15,28 @@ module.exports = class ItemGroupController extends BaseController constructor: (options={})-> if not options.imageLoader? then throw new Error 'options.imageLoader is required' if not options.modPack? then throw new Error 'options.modPack is required' + if not options.router? then throw new Error 'options.router is required' options.model ?= [] + options.templateName = 'common/item_group' options.title ?= '' - options.templateName = 'item_group' + options.tagName = 'section' super options - @_imageLoader = options.imageLoader - @_modPack = options.modPack - @_title = options.title + @_imageLoader = options.imageLoader + @_modPack = options.modPack + @_router = options.router + @_title = options.title # Property Methods ############################################################################# - getTitle: -> - return @_title - - setTitle: (title)-> - @_title = title - @tryRefresh() - Object.defineProperties @prototype, - title: {get:@prototype.getTitle, set:@prototype.setTitle} + + title: + get: -> @_title + + set: (newTitle)-> + @_title = newTitle + @tryRefresh() # BaseController Overrides ##################################################################### @@ -69,7 +68,11 @@ module.exports = class ItemGroupController extends BaseController for item in @model controller = @_itemControllers[controllerIndex] if not controller? - controller = new ItemController imageLoader:@_imageLoader, model:item, modPack:@_modPack + controller = new ItemController + imageLoader: @_imageLoader + model: item + modPack: @_modPack + router: @_router @_itemControllers.push controller @$items.append controller.$el controller.render() diff --git a/src/client/site/common/item_group/item_tile/item_tile.jade b/src/client/site/common/item_group/item_tile/item_tile.jade new file mode 100644 index 000000000..3cea7326a --- /dev/null +++ b/src/client/site/common/item_group/item_tile/item_tile.jade @@ -0,0 +1,11 @@ +//- +//- Crafting Guide - item_tile.jade +//- +//- Copyright (c) 2015 by Redwood Labs +//- All rights reserved. +//- + +.view__item_tile + a + img + p.itemName diff --git a/src/client/site/common/item_group/item_tile/item_tile.scss b/src/client/site/common/item_group/item_tile/item_tile.scss new file mode 100644 index 000000000..4b5543dbc --- /dev/null +++ b/src/client/site/common/item_group/item_tile/item_tile.scss @@ -0,0 +1,30 @@ +// +// Crafting Guide - item_tile.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__item_tile { + a { + overflow: visible; + + display: flex; + align-items: center; + + img { + height: $size-minecraft-block; + width: $size-minecraft-block; + margin-right: $size-margin-small; + } + + p { + font-family: $font-family-text; + font-size: $font-size-medium; + line-height: $size-minecraft-block; + overflow-x: hidden; + text-overflow: ellipsis; + white-space: nowrap; + } + } +} diff --git a/src/coffee/controllers/item_controller.coffee b/src/client/site/common/item_group/item_tile/item_tile_controller.coffee similarity index 66% rename from src/coffee/controllers/item_controller.coffee rename to src/client/site/common/item_group/item_tile/item_tile_controller.coffee index b7cd7a975..226455f1f 100644 --- a/src/coffee/controllers/item_controller.coffee +++ b/src/client/site/common/item_group/item_tile/item_tile_controller.coffee @@ -1,26 +1,25 @@ -### -Crafting Guide - item_controller.coffee +# +# Crafting Guide - item_group_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -_ = require 'underscore' +BaseController = require '../../../base_controller' ######################################################################################################################## -module.exports = class ItemController extends BaseController +module.exports = class ItemTileController extends BaseController constructor: (options={})-> if not options.imageLoader? then throw new Error 'options.imageLoader is required' if not options.model? then throw new Error 'options.model is required' if not options.modPack? then throw new Error 'options.modPack is required' - options.templateName = 'item' + options.templateName = 'common/item_group/item_tile' super options - @imageLoader = options.imageLoader - @modPack = options.modPack + @_imageLoader = options.imageLoader + @_modPack = options.modPack # BaseController Overrides ##################################################################### @@ -31,9 +30,9 @@ module.exports = class ItemController extends BaseController super refresh: -> - display = @modPack.findItemDisplay @model.slug + display = @_modPack.findItemDisplay @model.slug - @imageLoader.load display.iconUrl, @$icon + @_imageLoader.load display.iconUrl, @$icon @$name.html display.itemName @$nameLink.attr 'href', display.itemUrl diff --git a/src/client/site/common/item_selector/element/element.jade b/src/client/site/common/item_selector/element/element.jade new file mode 100644 index 000000000..a51521f10 --- /dev/null +++ b/src/client/site/common/item_selector/element/element.jade @@ -0,0 +1,11 @@ +//- +//- Crafting Guide - element.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__element + img + .name + .modName diff --git a/src/client/site/common/item_selector/element/element.scss b/src/client/site/common/item_selector/element/element.scss new file mode 100644 index 000000000..2fc1510b4 --- /dev/null +++ b/src/client/site/common/item_selector/element/element.scss @@ -0,0 +1,62 @@ +// +// Crafting Guide - element.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__element { + display : flex; + align-items: center; + + background: $color-white; + padding: $size-margin-xsmall $size-margin-medium; + + & > * { + margin-right: $size-margin-medium; + } + + & > :last-child { + margin-right: 0; + } + + img { + flex : 0 0 auto; + + height : $size-minecraft-block; + width : $size-minecraft-block; + } + + .name { + flex : 1 1 100%; + + color : $color-text; + font-family : $font-family-text; + font-size : $font-size-large; + } + + .modName { + flex : 0 0 auto; + + color : $color-text-secondary; + font-family : $font-family-text; + font-size : $font-size-small; + } + + &:nth-child(even) { + background : $color-gray-faint; + } + + &.selected { + flex : 0 0 auto; + background : $color-active-hover; + + .name { + color : $color-text-light; + } + + .modName { + color : $color-text-light; + } + } +} diff --git a/src/coffee/controllers/item_selector_element_controller.coffee b/src/client/site/common/item_selector/element/element_controller.coffee similarity index 75% rename from src/coffee/controllers/item_selector_element_controller.coffee rename to src/client/site/common/item_selector/element/element_controller.coffee index 77833b444..04560efc8 100644 --- a/src/coffee/controllers/item_selector_element_controller.coffee +++ b/src/client/site/common/item_selector/element/element_controller.coffee @@ -1,23 +1,21 @@ -### -Crafting Guide - item_selector_element_controller.coffee +# +# Crafting Guide - element.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -_ = require 'underscore' -{Event} = require '../constants' +BaseController = require '../../../base_controller' ######################################################################################################################## -module.exports = class ItemSelectorElementController extends BaseController +module.exports = class ElementController extends BaseController constructor: (options={})-> if not options.model? then throw new Error 'options.model is required' options.onClicked ?= (controller)-> # do nothing options.onSelected ?= (controller)-> # do nothing - options.templateName = 'item_selector_element' + options.templateName = 'common/item_selector/element' options.useAnimations = false super options @@ -36,8 +34,8 @@ module.exports = class ItemSelectorElementController extends BaseController @_selected = newSelected @tryRefresh() - @trigger Event.change + ':selected', this, oldSelected, newSelected - @trigger Event.change, this + @trigger c.event.change + ':selected', this, oldSelected, newSelected + @trigger c.event.change, this Object.defineProperties @prototype, selected: {get:@prototype.isSelected, set:@prototype.setSelected} @@ -46,8 +44,8 @@ module.exports = class ItemSelectorElementController extends BaseController onDidRender: -> @$icon = @$('img') - @$name = @$('.name p') - @$modName = @$('.modName p') + @$name = @$('.name') + @$modName = @$('.modName') super refresh: -> @@ -77,4 +75,4 @@ module.exports = class ItemSelectorElementController extends BaseController _onMouseEnter: (event)-> event.preventDefault() - @onSelected this \ No newline at end of file + @onSelected this diff --git a/src/client/site/common/item_selector/item_selector.jade b/src/client/site/common/item_selector/item_selector.jade new file mode 100644 index 000000000..8e8073b50 --- /dev/null +++ b/src/client/site/common/item_selector/item_selector.jade @@ -0,0 +1,14 @@ +//- +//- Crafting Guide - item_selector.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__item_selector + .view__item_selector_popup + .search + img(src='/images/search.png') + input(placeholder='enter the name of an item') + img.close(src='/images/close.png') + .results diff --git a/src/client/site/common/item_selector/item_selector.scss b/src/client/site/common/item_selector/item_selector.scss new file mode 100644 index 000000000..76996c0b9 --- /dev/null +++ b/src/client/site/common/item_selector/item_selector.scss @@ -0,0 +1,57 @@ +// +// Crafting Guide - item_selector.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__item_selector { +} + +.view__item_selector_popup { + height : 66%; + + background : $color-background-panel; + border : 1px solid $color-gray-medium; + + display: flex; + flex-direction: column; + + .search { + flex: 0 0 auto; + + border-bottom: 1px solid $color-gray-medium; + + display: flex; + padding: $size-margin-small; + + & > :not(:first-child) { + margin-left: $size-margin-medium; + } + + img { + flex: 0 0 auto; + } + + input { + flex: 1 1 100%; + + background: none; + border: 0; + font-family: $font-family-input; + font-size: $font-size-large; + outline: none; + } + + img.close { + cursor: pointer; + } + } + + .results { + flex: 1 1 100%; + + overflow-x: hidden; + overflow-y: scroll; + } +} diff --git a/src/coffee/controllers/item_selector_controller.coffee b/src/client/site/common/item_selector/item_selector_controller.coffee similarity index 65% rename from src/coffee/controllers/item_selector_controller.coffee rename to src/client/site/common/item_selector/item_selector_controller.coffee index 2211b015c..75b1a6845 100644 --- a/src/coffee/controllers/item_selector_controller.coffee +++ b/src/client/site/common/item_selector/item_selector_controller.coffee @@ -1,18 +1,13 @@ -### -Crafting Guide - item_selector_controller.coffee +# +# Crafting Guide - item_selector_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' -_ = require 'underscore' -BaseController = require './base_controller' -{Duration} = require '../constants' -{Event} = require '../constants' -ItemSelector = require '../models/item_selector' -ItemSelectorElementController = require './item_selector_element_controller' -{Key} = require '../constants' +BaseController = require '../../base_controller' +ItemSelector = require '../../../models/site/item_selector' +ElementController = require './element/element_controller' ######################################################################################################################## @@ -23,28 +18,63 @@ module.exports = class ItemSelectorController extends BaseController options.isAcceptable ?= null options.model ?= new ItemSelector {}, modPack:options.modPack, isAcceptable:options.isAcceptable options.onChoseItem ?= (item)-> # do nothing - options.templateName = 'item_selector' + options.templateName = 'common/item_selector' super options - @modPack = options.modPack - @onChoseItem = options.onChoseItem + @_modPack = options.modPack + @_session = null @_elementControllers = [] + # Public Methods ############################################################################### + + launch: (hint='')-> + if @_session + @_session.resolve null + @_session = null + + @model.hint = hint + if @rendered then @refresh() + + @_disableWindowScrolling() + + @$page.addClass 'blur' + @$screen.append @$popup + @$screen.css 'display', '' + + @$popup.off c.event.click + @$popup.on c.event.click, (event)=> @onPopupClicked(event) + + @$hintField.off 'keyup input' + @$hintField.on 'keyup', (event)=> @onHintKeyPress(event) + @$hintField.on 'input', (event)=> @onHintChanged(event) + @$hintField.focus() + + @$closeButton.one 'click', (event)=> @_close() + + @$screen.one c.event.click, (event)=> @onScreenClicked(event) + + @_session = w.defer() + return @_session.promise + # Event Methods ################################################################################ + onClose: (event)-> + @_close() + return false + onHintKeyPress: (event)-> switch event.which - when Key.Escape + when c.key.escape @_close() return false - when Key.Enter + when c.key.enter @_chooseSelected() return false - when Key.DownArrow + when c.key.down @_selectNext() return false - when Key.UpArrow + when c.key.up @_selectPrevious() return false @@ -53,39 +83,13 @@ module.exports = class ItemSelectorController extends BaseController @tryRefresh() @onResultSelected @_elementControllers[0] - onLaunchButtonClicked: (event)-> - event.preventDefault() - @model.hint = '' - @refresh() - - $('body').addClass 'stop-scrolling' - - @$screen.append @$popup - @$screen.css 'display', 'block' - - @$popup.offset @$el.offset() - @$popup.css 'width', @$el.css 'width' - @$popup.off Event.click - @$popup.on Event.click, (event)=> @onPopupClicked(event) - @$popup.removeClass 'hiding' - - @$hintField.off 'keyup input' - @$hintField.on 'keyup', (event)=> @onHintKeyPress(event) - @$hintField.on 'input', (event)=> @onHintChanged(event) - - @$popup.off Event.transitionEnd - @$popup.one Event.transitionEnd, => @onPopupDisplayed() - @$screen.one Event.click, (event)=> @onScreenClicked(event) - onPopupClicked: (event)-> return false - onPopupDisplayed: -> - @$hintField.focus() - onResultClicked: (controller)-> + @_session.resolve controller.model.slug + @_session = null @_close() - @onChoseItem controller.model.slug onResultSelected: (controller)-> for c in @_elementControllers @@ -101,7 +105,10 @@ module.exports = class ItemSelectorController extends BaseController # BaseController Overrides ##################################################################### onDidRender: -> + @$page = $('.page') # find the shared, global page @$screen = $('.view__screen') # find the shared, global screen + + @$closeButton = @$('img.close') @$popup = @$('.view__item_selector_popup') @$hintField = @$('.view__item_selector_popup input') @$searchInput = @$('.search input') @@ -115,17 +122,6 @@ module.exports = class ItemSelectorController extends BaseController @_refreshResults() super - render: -> - $buttonContent = @$el.html() - super - @$el.html $buttonContent - - # Backbone.View Overrides ###################################################################### - - events: -> - return _.extend super, - 'click': 'onLaunchButtonClicked' - # Private Methods ############################################################################## _chooseSelected: -> @@ -135,24 +131,28 @@ module.exports = class ItemSelectorController extends BaseController return _close: -> - $('body').removeClass 'stop-scrolling' + @_enableWindowScrolling() + @$page.removeClass 'blur' + @$screen.css 'display', 'none' + @$popup.detach() + @model.hint = '' - @$popup.addClass 'hiding' + _disableWindowScrolling: -> + @_windowScrollPosition = $(window).scrollTop() + $('body').addClass('scrollDisabled').css('margin-top', -@_windowScrollPosition) - @$popup.off Event.transitionEnd - @$popup.one Event.transitionEnd, => - @$screen.css 'display', 'none' - @$popup.detach() - @model.hint = '' + _enableWindowScrolling: -> + $('body').removeClass('scrollDisabled').css('margin-top', 0) + $(window).scrollTop @_windowScrollPosition _refreshResults: -> index = 0 for itemSlug in @model.results - displayModel = @modPack.findItemDisplay itemSlug + displayModel = @_modPack.findItemDisplay itemSlug controller = @_elementControllers[index] if not controller? - controller = new ItemSelectorElementController + controller = new ElementController model: displayModel onClicked: (c)=> @onResultClicked(c) onSelected: (c)=> @onResultSelected(c) @@ -192,4 +192,4 @@ module.exports = class ItemSelectorController extends BaseController _showElement: ($el)-> top = $el.position().top + @$resultsContainer.scrollTop() - @$resultsContainer.animate {scrollTop:top}, duration:Duration.snap + @$resultsContainer.css 'scrollTop', top diff --git a/src/jade/templates/markdown_image.jade b/src/client/site/common/markdown_section/markdown_image_list/markdown_image/markdown_image.jade similarity index 71% rename from src/jade/templates/markdown_image.jade rename to src/client/site/common/markdown_section/markdown_image_list/markdown_image/markdown_image.jade index de5a26ec3..c97cbd8bd 100644 --- a/src/jade/templates/markdown_image.jade +++ b/src/client/site/common/markdown_section/markdown_image_list/markdown_image/markdown_image.jade @@ -1,7 +1,7 @@ //- //- Crafting Guide - markdown_image.jade //- -//- Copyright (c) 2015 by Redwood Labs +//- Copyright © 2014-2016 by Redwood Labs //- All rights reserved. //- @@ -9,8 +9,9 @@ .loaded .thumbnail: img .dynamic + .button: .bezel: p .fileName: p .error: p - button form: input(type="file", accept="image/gif,image/jpeg,image/png" multiple="false") - .loading: p checking for image... + .loading + p checking for image... diff --git a/src/client/site/common/markdown_section/markdown_image_list/markdown_image/markdown_image.scss b/src/client/site/common/markdown_section/markdown_image_list/markdown_image/markdown_image.scss new file mode 100644 index 000000000..e423b103c --- /dev/null +++ b/src/client/site/common/markdown_section/markdown_image_list/markdown_image/markdown_image.scss @@ -0,0 +1,71 @@ +// +// Crafting Guide - markdown_image.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__markdown_image { + display: flex; + flex-direction: column; + + .loaded { + display: flex; + + .thumbnail { + flex: 0 0 auto; + height: $size-minecraft-block * 4; + width: $size-minecraft-block * 4; + margin-right: $size-margin-medium; + + background: $color-gray-faint; + border: 1px solid $color-gray-light; + + display: flex; + justify-content: center; + align-items: center; + + img { + width: $size-minecraft-block * 3; + max-height: $size-minecraft-block * 3; + } + } + + .dynamic { + flex: 1 1 100%; + + & > :not(:last-child) { + margin-bottom: $size-margin-medium; + } + + .fileName { + font-family: $font-family-control; + font-size: $font-size-medium; + } + + .error { + color: $color-error; + font-family: $font-family-control; + font-size: $font-size-small; + } + } + + form { + display: none; + } + } + + .loading { + height: $size-minecraft-block * 4; + + display: flex; + justify-content: center; + align-items: center; + + p { + color: $color-gray-light; + font-family: $font-family-control; + font-size: $font-size-medium; + } + } +} \ No newline at end of file diff --git a/src/coffee/controllers/markdown_image_controller.coffee b/src/client/site/common/markdown_section/markdown_image_list/markdown_image/markdown_image_controller.coffee similarity index 76% rename from src/coffee/controllers/markdown_image_controller.coffee rename to src/client/site/common/markdown_section/markdown_image_list/markdown_image/markdown_image_controller.coffee index 93eba14c2..e6c515054 100644 --- a/src/coffee/controllers/markdown_image_controller.coffee +++ b/src/client/site/common/markdown_section/markdown_image_list/markdown_image/markdown_image_controller.coffee @@ -5,23 +5,20 @@ Copyright (c) 2015 by Redwood Labs All rights reserved. ### -$ = require 'jquery' -_ = require 'underscore' -BaseController = require './base_controller' -{Duration} = require '../constants' -MarkdownImage = require '../models/markdown_image' +BaseController = require '../../../../base_controller' +MarkdownImage = require '../../../../../models/site/markdown_image' ######################################################################################################################## module.exports = class MarkdownImageController extends BaseController - MAX_FILE_SIZE = 750 * 1024 - MAX_HEIGHT = 600 - MAX_WIDTH = 740 + @::MAX_FILE_SIZE = 750 * 1024 + @::MAX_HEIGHT = 600 + @::MAX_WIDTH = 740 constructor: (options={})-> if not options.model? then throw new Error 'options.model is required' - options.templateName = 'markdown_image' + options.templateName = 'common/markdown_section/markdown_image_list/markdown_image' super @_errorMessage = null @@ -37,9 +34,9 @@ module.exports = class MarkdownImageController extends BaseController file = @$input.prop('files')[0] return unless file? - if file.size > MAX_FILE_SIZE + if file.size > @MAX_FILE_SIZE logger.warning "The choosen file, #{file.name}, is too large: #{file.size}" - @errorMessage = "Choose a file less than #{MAX_FILE_SIZE / 1024}kB" + @errorMessage = "Choose a file less than #{@MAX_FILE_SIZE / 1024}kB" @_clearFile() return @@ -55,15 +52,15 @@ module.exports = class MarkdownImageController extends BaseController $image = $("") $image.load => - if $image[0].naturalHeight > MAX_HEIGHT + if $image[0].naturalHeight > @MAX_HEIGHT logger.warning "The choosen file, #{file.name}, is too tall: #{$image[0].naturalHeight}" - @errorMessage = "Choose an image less than #{MAX_HEIGHT}px tall" + @errorMessage = "Choose an image less than #{@MAX_HEIGHT}px tall" @_clearFile() return - if $image[0].naturalWidth > MAX_WIDTH + if $image[0].naturalWidth > @MAX_WIDTH logger.warning "The choosen file, #{file.name}, is too wide: #{$image[0].naturalWidth}" - @errorMessage = "Choose an image less than #{MAX_WIDTH}px wide" + @errorMessage = "Choose an image less than #{@MAX_WIDTH}px wide" @_clearFile() return @@ -106,7 +103,7 @@ module.exports = class MarkdownImageController extends BaseController onDidRender: -> @$image = @$('img') @$fileName = @$('.fileName p') - @$button = @$('button') + @$buttonLabel = @$('.button p') @$form = @$('form') @$input = @$('input') @$errorContainer = @$('.error') @@ -116,6 +113,10 @@ module.exports = class MarkdownImageController extends BaseController super + onWillChangeModel: (oldModel, newModel)-> + @errorMessage = null + super oldModel, newModel + refresh: -> if @model.mimeType? and @model.encodedData? @$image.attr 'src', "data:#{@model.mimeType};base64,#{@model.encodedData}" @@ -125,25 +126,25 @@ module.exports = class MarkdownImageController extends BaseController @$fileName.html @model.fileName if @model.encodedData? - @$button.html 'Update' + @$buttonLabel.html 'Update' else - @$button.html 'Choose' + @$buttonLabel.html 'Choose' - if @model.status is MarkdownImage.Status.checking - @$loaded.fadeOut duration:Duration.normal - @$loading.fadeIn duration:Duration.normal, queue:true + if @model.status is MarkdownImage::Status.checking + @hide @$loaded + @show @$loading else - @$loading.fadeOut duration:Duration.normal - @$loaded.fadeIn duration:Duration.normal, queue:true + @hide @$loading + @show @$loaded if @errorMessage? @$errorMessage.html @errorMessage - @$errorContainer.fadeIn duration:Duration.normal - else if @model.status is MarkdownImage.Status.empty + @show @$errorContainer + else if @model.status is MarkdownImage::Status.empty @$errorMessage.html 'please choose an image' - @$errorContainer.fadeIn duration:Duration.normal + @show @$errorContainer else - @$errorContainer.fadeOut duration:Duration.normal + @hide @$errorContainer super @@ -151,7 +152,7 @@ module.exports = class MarkdownImageController extends BaseController events: -> return _.extend super, - 'click button': 'onButtonClicked' + 'click .button': 'onButtonClicked' 'change input': 'onFileChanged' # Private Methods ############################################################################## diff --git a/src/jade/templates/markdown_image_list.jade b/src/client/site/common/markdown_section/markdown_image_list/markdown_image_list.jade similarity index 68% rename from src/jade/templates/markdown_image_list.jade rename to src/client/site/common/markdown_section/markdown_image_list/markdown_image_list.jade index 376cdb5db..b660423db 100644 --- a/src/jade/templates/markdown_image_list.jade +++ b/src/client/site/common/markdown_section/markdown_image_list/markdown_image_list.jade @@ -1,10 +1,10 @@ //- //- Crafting Guide - markdown_image_list.jade //- -//- Copyright (c) 2015 by Redwood Labs +//- Copyright © 2014-2016 by Redwood Labs //- All rights reserved. //- .view__markdown_image_list h3 Images Referenced - .image_container \ No newline at end of file + .image_container diff --git a/src/client/site/common/markdown_section/markdown_image_list/markdown_image_list.scss b/src/client/site/common/markdown_section/markdown_image_list/markdown_image_list.scss new file mode 100644 index 000000000..2396e5745 --- /dev/null +++ b/src/client/site/common/markdown_section/markdown_image_list/markdown_image_list.scss @@ -0,0 +1,29 @@ +// +// Crafting Guide - markdown_image_list.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__markdown_image_list { + position: relative; min-width: 33em; width: 100%; + + border-bottom: 0.1em solid $color-gray-medium; + margin: 2em 0; + padding: 0 0 2em 0; + + h3 { + margin-bottom: 1em; + } + + .image_container { + display: flex; + flex-wrap: wrap; + margin-right: -$size-margin-large; + + & > * { + width: calc(50% - 24px); // $size-margin-large + margin-right: $size-margin-large; + } + } +} diff --git a/src/coffee/controllers/markdown_image_list_controller.coffee b/src/client/site/common/markdown_section/markdown_image_list/markdown_image_list_controller.coffee similarity index 79% rename from src/coffee/controllers/markdown_image_list_controller.coffee rename to src/client/site/common/markdown_section/markdown_image_list/markdown_image_list_controller.coffee index a802ed78b..235931f4e 100644 --- a/src/coffee/controllers/markdown_image_list_controller.coffee +++ b/src/client/site/common/markdown_section/markdown_image_list/markdown_image_list_controller.coffee @@ -1,14 +1,13 @@ -### -Crafting Guide - markdown_image_list_controller.coffee +# +# Crafting Guide - markdown_image_list_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -{Event} = require '../constants' -MarkdownImageController = require './markdown_image_controller' -MarkdownImageList = require '../models/markdown_image_list' +BaseController = require '../../../base_controller' +MarkdownImageController = require './markdown_image/markdown_image_controller' +MarkdownImageList = require '../../../../models/site/markdown_image_list' ######################################################################################################################## @@ -16,7 +15,7 @@ module.exports = class MarkdownImageListController extends BaseController constructor: (options={})-> options.model ?= new MarkdownImageList {}, {client:options.client} - options.templateName = 'markdown_image_list' + options.templateName = 'common/markdown_section/markdown_image_list' super options @imageBase = '' @@ -43,8 +42,8 @@ module.exports = class MarkdownImageListController extends BaseController return unless oldImageBase isnt newImageBase @_imageBase = newImageBase - @trigger Event.change + ':imageBase', this, oldImageBase, newImageBase - @trigger Event.change, this + @trigger c.event.change + ':imageBase', this, oldImageBase, newImageBase + @trigger c.event.change, this getMarkdownText: -> return @model.markdownText @@ -96,5 +95,5 @@ module.exports = class MarkdownImageListController extends BaseController return if newValid is oldValid @_valid = newValid - @trigger Event.change + ':valid', this, oldValid, newValid - @trigger Event.change + @trigger c.event.change + ':valid', this, oldValid, newValid + @trigger c.event.change diff --git a/src/client/site/common/markdown_section/markdown_section.jade b/src/client/site/common/markdown_section/markdown_section.jade new file mode 100644 index 000000000..036221930 --- /dev/null +++ b/src/client/site/common/markdown_section/markdown_section.jade @@ -0,0 +1,38 @@ +//- +//- Crafting Guide - markdown_section.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__markdown_section + h2 + .panel + .waiting: img(src='/images/wait.gif') + .markdown + .creating + p Please help by adding a description! + .editor + .instructions. + Edit using GitHub + Flavored Markdown. Use [[Item Name]] to link to another item and ![](image.png) + to add an image. + .text + textarea + .sizer + .view__markdown_image_list + .footer + .question: a(href="javascript:void;") Confused? Click here to ask a question! + .error: p + .buttons + .button.edit: .bezel: p edit + .button.save: .bezel: p save + .button.preview: .bezel: p preview + .button.cancel: .bezel: p cancel + .button.return: .bezel: p return + .confirming + p Thanks for your help! + p Your changes will appear on the site in a few minutes. + .appologizing + p Sorry, but something went wrong. + p Please try again after a few moments. \ No newline at end of file diff --git a/src/client/site/common/markdown_section/markdown_section.scss b/src/client/site/common/markdown_section/markdown_section.scss new file mode 100644 index 000000000..b7ed70385 --- /dev/null +++ b/src/client/site/common/markdown_section/markdown_section.scss @@ -0,0 +1,130 @@ +// +// Crafting Guide - markdown_section.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__markdown_section { + display : flex; + flex-direction : column; + + .waiting { + display : flex; + justify-content : center; + + padding : $size-margin-xlarge; + } + + .appologizing, .confirming, .creating { + display : flex; + flex-direction : column; + justify-content : center; + padding : $size-margin-xlarge; + + p { + color : $color-gray-medium; + font-family : $font-family-text; + font-size : $font-size-large; + text-align : center; + + &:not(:first-child) { + margin-top: $size-margin-medium; + } + } + } + + .creating { + padding-bottom: $size-margin-large; + + p { + color: $color-gray-light; + font-size: $font-size-xlarge; + } + } + + .editor { + display : flex; + flex-direction : column; + + .instructions { + margin-bottom : $size-margin-medium; + + color : $color-gray-medium; + font-family : $font-family-text; + font-size : $font-size-small; + } + + .text { + display : flex; + flex-direction : column; + position : relative; + + textarea, .sizer { + font-family : $font-family-input; + font-size : $font-size-medium; + line-height : $font-size-medium; + overflow : hidden; + padding : $size-margin-small; + resize : none; + white-space : pre-wrap; + } + + textarea { + position : absolute; width: 100%; height: 100%; + + background: none; + z-index: $layer-normal; + } + + .sizer { + min-height: $size-minecraft-block * 4; + opacity: 0; + z-index: $layer-normal - 1; + } + } + } + + .footer { + display : flex; + align-items : flex-end; + margin-top : $size-margin-large; + + .question { + flex : 1 1 100%; + + a { + color : $color-gray-light; + font-family : $font-family-text; + font-size : $font-size-medium; + text-decoration : underline; + } + } + + .error { + flex: 1 1 100%; + align-self: center; + + p { + color : $color-error; + font-family : $font-family-text; + font-size : $font-size-medium; + font-style : italic; + text-align : center; + } + } + + .buttons { + flex : 0 0 auto; + + display : flex; + flex-direction : row-reverse; + align-items : center; + + .button { + margin-left : $size-margin-medium; + width : $size-minecraft-block * 5; + } + } + } +} diff --git a/src/coffee/controllers/markdown_section_controller.coffee b/src/client/site/common/markdown_section/markdown_section_controller.coffee similarity index 60% rename from src/coffee/controllers/markdown_section_controller.coffee rename to src/client/site/common/markdown_section/markdown_section_controller.coffee index e13dc6f88..41c4786d0 100644 --- a/src/coffee/controllers/markdown_section_controller.coffee +++ b/src/client/site/common/markdown_section/markdown_section_controller.coffee @@ -1,24 +1,19 @@ -### -Crafting Guide - markdown_section_controller.coffee +# +# Crafting Guide - markdown_section_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' -BaseController = require './base_controller' +BaseController = require '../../base_controller' convertMarkdown = require 'marked' -{Duration} = require '../constants' -{Event} = require '../constants' -MarkdownImageListController = require './markdown_image_list_controller' -{Url} = require '../constants' -w = require 'when' +MarkdownImageListController = require './markdown_image_list/markdown_image_list_controller' ######################################################################################################################## module.exports = class MarkdownSectionController extends BaseController - @State = State = + @::State = appologizing: 'applogizing' confirming: 'confirming' creating: 'creating' @@ -30,19 +25,17 @@ module.exports = class MarkdownSectionController extends BaseController constructor: (options={})-> if not options.modPack? then throw new Error 'options.modPack is required' options.model ?= null - options.templateName = 'markdown_section' - @_state = State.waiting + options.templateName = 'common/markdown_section' + @_state = @State.waiting super options - @on Event.animate.hide.finish, => @_updateStateVisibility() - @on Event.animate.show.finish, => @_updateStateVisibility() - - @client = options.client - @confirmactionMessage = options.confirmationMessage - @confirmDuration = options.confirmationDuration ?= 5000 - @imageBase = options.imageBase ?= '' - @modPack = options.modPack - @title = options.title ?= 'Description' + @_client = options.client + @_confirmationMessage = options.confirmationMessage + @_confirmDuration = options.confirmationDuration or 5000 + @_enterFeedback = options.enterFeedback or -> # do nothing + @_imageBase = options.imageBase or '' + @_modPack = options.modPack + @_title = options.title or 'Description' # @_beginEditing must be a function returning a promise which resolves when all actions necessary prior to an # editing session have been completed (e.g., loading the latest content from a remote server). The promise must @@ -57,12 +50,12 @@ module.exports = class MarkdownSectionController extends BaseController resetToDefaultState: -> if @model? - @state = State.viewing + @state = @State.viewing else if @editable? - @state = State.creating + @state = @State.creating else - @state = State.waiting + @state = @State.waiting # Event Methods ################################################################################ @@ -79,42 +72,42 @@ module.exports = class MarkdownSectionController extends BaseController return unless @editable @_originalModel = @model - @state = State.waiting + @state = @State.waiting @_beginEditing() .then => - @state = State.editing + @state = @State.editing .catch (e)=> logger.warning "cannot begin editing: #{e.stack}" - @state = State.appologizing - w(true).delay(@confirmDuration).then => @resetToDefaultState() + @state = @State.appologizing + w(true).delay(@_confirmDuration).then => @resetToDefaultState() onQuestionClicked: (event)-> event.preventDefault() - global.feedbackController.enterFeedback '' + @_enterFeedback '' onPreviewClicked: (event)-> event.preventDefault() @_updatePreview() - @state = State.previewing + @state = @State.previewing onReturnClicked: (event)-> event.preventDefault() - @state = State.editing + @state = @State.editing onSaveClicked: (event)-> event.preventDefault() - @state = State.waiting + @state = @State.waiting @_endEditing() .then => - @state = State.confirming + @state = @State.confirming .catch (e)=> message = if e.stack? then e.stack else e logger.error "failed to end editing: #{message}" - @state = State.appologizing - .delay @confirmDuration + @state = @State.appologizing + .delay @_confirmDuration .then => - @state = State.viewing + @state = @State.viewing onTextChanged: (event)-> event.preventDefault() @@ -133,8 +126,8 @@ module.exports = class MarkdownSectionController extends BaseController return unless newImageBase isnt oldImageBase @_imageBase = newImageBase - @trigger Event.change + ':imageBase', this, oldImageBase, newImageBase - @trigger Event.change, this + @trigger c.event.change + ':imageBase', this, oldImageBase, newImageBase + @trigger c.event.change, this getImageFiles: -> return @_imageListController.model.all @@ -148,7 +141,7 @@ module.exports = class MarkdownSectionController extends BaseController @_state = newState logger.verbose => "MarkdownSectionController.#{@cid} changed state from #{oldState} to #{newState}" - @trigger Event.change + ':state', this, oldState, newState + @trigger c.event.change + ':state', this, oldState, newState @tryRefresh() Object.defineProperties @prototype, @@ -160,19 +153,18 @@ module.exports = class MarkdownSectionController extends BaseController # BaseController Overrides ##################################################################### onDidRender: -> - @_imageListController = @addChild MarkdownImageListController, '.image_list', - client: @client - imageBase: @imageBase - @on Event.change + ':imageBase', => @_imageListController.model.imageBase = @imageBase - @listenTo @_imageListController, Event.change + ':valid', => @tryRefresh() - - if not global.feedbackController? - @$('.question').hide duration:0 + @_imageListController = @addChild MarkdownImageListController, '.view__markdown_image_list', + client: @_client + imageBase: @_imageBase + @on c.event.change + ':imageBase', => @_imageListController.model.imageBase = @_imageBase + @listenTo @_imageListController, c.event.change + ':valid', => @tryRefresh() + @$errorPanel = @$('.error') @$errorText = @$('.error p') @$markdownPanel = @$('.markdown') - @$previewButton = @$('button.preview') - @$saveButton = @$('button.save') + @$previewButton = @$('.button.preview') + @$questionPanel = @$('.question') + @$saveButton = @$('.button.save') @$sizer = @$('.sizer') @$textarea = @$('textarea') @$title = @$('h2') @@ -182,9 +174,9 @@ module.exports = class MarkdownSectionController extends BaseController super refresh: -> - @$title.html @title + @$title.html @_title @_imageListController.markdownText = @model - @_imageListController.fetchImages() if @state is State.editing + @_imageListController.fetchImages() if @state is @State.editing @_updateButtonStates() @_updateSizer() @@ -201,14 +193,14 @@ module.exports = class MarkdownSectionController extends BaseController events: -> return _.extend super, - 'click .markdown a': 'routeLinkClick' - 'click button.cancel': 'onCancelClicked' - 'click button.edit': 'onEditClicked' - 'click button.preview': 'onPreviewClicked' - 'click button.return': 'onReturnClicked' - 'click button.save': 'onSaveClicked' - 'click .question a': 'onQuestionClicked' - 'input textarea': 'onTextChanged' + 'click .markdown a': 'routeLinkClick' + 'click .button.cancel': 'onCancelClicked' + 'click .button.edit': 'onEditClicked' + 'click .button.preview': 'onPreviewClicked' + 'click .button.return': 'onReturnClicked' + 'click .button.save': 'onSaveClicked' + 'click .question a': 'onQuestionClicked' + 'input textarea': 'onTextChanged' # Private Methods ############################################################################## @@ -219,9 +211,9 @@ module.exports = class MarkdownSectionController extends BaseController _convertWikiLinks: (text)-> text.replace /\[\[([^\]]*)\]\]/g, (match, name)=> result = match - item = @modPack.findItemByName name + item = @_modPack.findItemByName name if item? - display = @modPack.findItemDisplay item.slug + display = @_modPack.findItemDisplay item.slug result = "[#{name}](#{display.itemUrl})" return result @@ -257,53 +249,50 @@ module.exports = class MarkdownSectionController extends BaseController elements = appologizingPanel: @$('.appologizing') - buttonPanel: @$('.buttons') - cancelButton: @$('button.cancel') + cancelButton: @$('.button.cancel') confirmingPanel: @$('.confirming') creatingPanel: @$('.creating') - editButton: @$('button.edit') + editButton: @$('.button.edit') editorPanel: @$('.editor') - errorPanel: @$('.error') - imageList: @$('.image_list') + footerPanel: @$('.footer') + imageList: @$('.view__markdown_image_list') markdownPanel: @$markdownPanel previewButton: @$previewButton - returnButton: @$('button.return') + returnButton: @$('.button.return') saveButton: @$saveButton waitingPanel: @$('.waiting') visible = {} errorText = '' - if @state is State.appologizing + if @state is @State.appologizing visible = appologizingPanel:true - else if @state is State.confirming + else if @state is @State.confirming visible = confirmingPanel:true - else if @state is State.creating - visible = buttonPanel:true, creatingPanel:true, editButton:true - else if @state is State.editing - visible = buttonPanel:true, cancelButton:true, editorPanel:true, previewButton:true, imageList:true - else if @state is State.previewing - visible = buttonPanel:true, errorPanel:true, markdownPanel:true, returnButton:true, saveButton:true + else if @state is @State.creating + visible = footerPanel:true, creatingPanel:true, editButton:true + else if @state is @State.editing + visible = footerPanel:true, editorPanel:true, cancelButton:true, previewButton:true, imageList:true + else if @state is @State.previewing + visible = footerPanel:true, markdownPanel:true, returnButton:true, saveButton:true errorText = "remember: your changes aren't saved yet!" - else if @state is State.viewing + else if @state is @State.viewing visible = markdownPanel:true - if @editable then _.extend visible, {buttonPanel:true, editButton:true} + if @editable then _.extend visible, {footerPanel:true, editButton:true} else # assume any unknown state is the same as "waiting" visible = waitingPanel:true - toHide = ($el for name, $el of elements when not visible[name]) - toShow = ($el for name, $el of elements when visible[name]) + for name, $el of elements when not visible[name] + @hide $el + for name, $el of elements when visible[name] + @show $el - $el.clearQueue() for name, $el of elements - - if toHide.length > 0 - $el.fadeOut(duration:Duration.normal) for $el in toHide - $el.delay(Duration.normal) for $el in toShow - - $el.fadeIn(duration:Duration.normal) for $el in toShow - - if @state is State.editing - @once Event.animate.show.finish, => - @$textarea.focus() + if @state is @State.editing then @$textarea.focus() @$errorText.html errorText + if errorText.length > 0 + @show @$errorPanel + @hide @$questionPanel + else + @hide @$errorPanel + @show @$questionPanel diff --git a/src/jade/templates/minimal_recipe.jade b/src/client/site/common/recipe/recipe.jade similarity index 56% rename from src/jade/templates/minimal_recipe.jade rename to src/client/site/common/recipe/recipe.jade index 63f010f22..0acf46b76 100644 --- a/src/jade/templates/minimal_recipe.jade +++ b/src/client/site/common/recipe/recipe.jade @@ -1,13 +1,14 @@ //- -//- Crafting Guide - minimal_recipe.jade +//- Crafting Guide - recipe.jade //- //- Copyright (c) 2015 by Redwood Labs //- All rights reserved. //- -.view__minimal_recipe +.view__recipe .input .view__crafting_grid .tool - .output.view__slot - .multiplier \ No newline at end of file + .output + .view__slot + .multiplier \ No newline at end of file diff --git a/src/client/site/common/recipe/recipe.scss b/src/client/site/common/recipe/recipe.scss new file mode 100644 index 000000000..6ae4b3584 --- /dev/null +++ b/src/client/site/common/recipe/recipe.scss @@ -0,0 +1,45 @@ +// +// Crafting Guide - recipe.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__recipe { + display: flex; + + .input { + flex: 1 1 50%; + + align-items : center; + display : flex; + flex-direction : column; + + .tool { + margin-top : $size-margin-small; + + font-family : $font-family-text; + font-size : $font-size-medium; + } + } + + .output { + flex: 1 1 50%; + margin-left: $size-margin-medium; + + display : flex; + flex-direction : column; + justify-content : center; + align-items : center; + + .view__slot { + border: $size-border-medium solid $color-gray-medium; + } + + .multiplier { + font-family : $font-family-header; + font-size : $font-size-large; + margin-top : $size-margin-medium; + } + } +} diff --git a/src/coffee/controllers/minimal_recipe_controller.coffee b/src/client/site/common/recipe/recipe_controller.coffee similarity index 64% rename from src/coffee/controllers/minimal_recipe_controller.coffee rename to src/client/site/common/recipe/recipe_controller.coffee index 4c01aa9a5..274d40566 100644 --- a/src/coffee/controllers/minimal_recipe_controller.coffee +++ b/src/client/site/common/recipe/recipe_controller.coffee @@ -1,42 +1,43 @@ -### -Crafting Guide - minimal_recipe_controller.coffee +# +# Crafting Guide - recipe_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -CraftingGridController = require './crafting_grid_controller' -ImageLoader = require './image_loader' -SlotController = require './slot_controller' -_ = require 'underscore' -{Duration} = require '../constants' +BaseController = require '../../base_controller' +CraftingGridController = require '../crafting_grid/crafting_grid_controller' +SlotController = require '../slot/slot_controller' {StringBuilder} = require 'crafting-guide-common' ######################################################################################################################## -module.exports = class MinimalRecipeController extends BaseController +module.exports = class RecipeController extends BaseController constructor: (options={})-> if not options.imageLoader? then throw new Error 'options.imageLoader is required' if not options.modPack? then throw new Error 'options.modPack is required' - options.templateName = 'minimal_recipe' + if not options.router? then throw new Error 'options.router is required' + options.templateName = 'common/recipe' super options - @imageLoader = options.imageLoader - @modPack = options.modPack - @multiplier = options.multiplier + @_imageLoader = options.imageLoader + @_modPack = options.modPack + @_multiplier = options.multiplier + @_router = options.router # BaseController Overrides ##################################################################### onDidRender: -> - @gridController = @addChild CraftingGridController, '.view__crafting_grid', - modPack: @modPack - imageLoader: @imageLoader + @_gridController = @addChild CraftingGridController, '.view__crafting_grid', + modPack: @_modPack + imageLoader: @_imageLoader + router: @_router - @outputSlotController = @addChild SlotController, '.output.view__slot', - imageLoader: @imageLoader - modPack: @modPack + @_outputSlotController = @addChild SlotController, '.output .view__slot', + imageLoader: @_imageLoader + modPack: @_modPack + router: @_router @$multiplier = @$('.multiplier') @$outputImg = @$('.output img') @@ -46,8 +47,8 @@ module.exports = class MinimalRecipeController extends BaseController super refresh: -> - @gridController.model = @model - @outputSlotController.model = @model?.output?[0] + @_gridController.model = @model + @_outputSlotController.model = @model?.output?[0] @_refreshMultiplier() @_refreshTools() @@ -91,6 +92,6 @@ module.exports = class MinimalRecipeController extends BaseController builder = new StringBuilder builder.loop @model.tools, delimiter:', ', onEach:(b, stack)=> - display = @modPack.findItemDisplay stack.itemSlug + display = @_modPack.findItemDisplay stack.itemSlug b.push "#{display.itemName}" @$toolContainer.html builder.toString() diff --git a/src/jade/templates/slot.jade b/src/client/site/common/slot/slot.jade similarity index 100% rename from src/jade/templates/slot.jade rename to src/client/site/common/slot/slot.jade diff --git a/src/client/site/common/slot/slot.scss b/src/client/site/common/slot/slot.scss new file mode 100644 index 000000000..61f853777 --- /dev/null +++ b/src/client/site/common/slot/slot.scss @@ -0,0 +1,30 @@ +// +// Crafting Guide - slot.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__slot { + position : relative; + height : ($size-minecraft-block * 1.5) + ($size-margin-xsmall * 2); + width : ($size-minecraft-block * 1.5) + ($size-margin-xsmall * 2); + + display : flex; + align-items : center; + justify-content : center; + padding : $size-margin-xsmall; + + img { + height: $size-minecraft-block * 1.5; + width: $size-minecraft-block * 1.5; + } + + .quantity { + position : absolute; right: 2px; bottom: 0; + color : white; + font-family : $font-family-header; + font-size : $font-size-large; + text-shadow : -2px -2px 0 #000, 2px -2px 0 #000, -2px 2px 0 #000, 2px 2px 0 #000; + } +} diff --git a/src/coffee/controllers/slot_controller.coffee b/src/client/site/common/slot/slot_controller.coffee similarity index 70% rename from src/coffee/controllers/slot_controller.coffee rename to src/client/site/common/slot/slot_controller.coffee index 1caddbdb5..d6d02f90f 100644 --- a/src/coffee/controllers/slot_controller.coffee +++ b/src/client/site/common/slot/slot_controller.coffee @@ -1,12 +1,11 @@ -### -Crafting Guide - slot_controller.coffee +# +# Crafting Guide - slot_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -_ = require 'underscore' +BaseController = require '../../base_controller' ######################################################################################################################## @@ -15,13 +14,15 @@ module.exports = class SlotController extends BaseController constructor: (options={})-> if not options.imageLoader? then throw new Error 'options.imageLoader is required' if not options.modPack? then throw new Error 'options.modPack is required' + if not options.router? then throw new Error 'options.router is required' # options.model should be a Stack - options.templateName = 'slot' + options.templateName = 'common/slot' options.useAnimations = false super options - @imageLoader = options.imageLoader - @modPack = options.modPack + @_imageLoader = options.imageLoader + @_modPack = options.modPack + @_router = options.router # BaseController Overrides ##################################################################### @@ -33,10 +34,10 @@ module.exports = class SlotController extends BaseController refresh: -> if @model? - display = @modPack.findItemDisplay @model.itemSlug + display = @_modPack.findItemDisplay @model.itemSlug @$link.attr 'href', display.itemUrl - @imageLoader.load display.iconUrl, @$image + @_imageLoader.load display.iconUrl, @$image if @model.quantity > 1 @$quantity.html @model.quantity diff --git a/src/client/site/common/stack/stack.jade b/src/client/site/common/stack/stack.jade new file mode 100644 index 000000000..a152ced01 --- /dev/null +++ b/src/client/site/common/stack/stack.jade @@ -0,0 +1,15 @@ +//- +//- Crafting Guide - stack.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__stack + .quantity: input + .icon: img(src='') + .name: a + .action.first(style="display: none") + .button: .bezel: p   + .action.second(style="display: none") + .button: .bezel: p   diff --git a/src/client/site/common/stack/stack.scss b/src/client/site/common/stack/stack.scss new file mode 100644 index 000000000..f7cc0000d --- /dev/null +++ b/src/client/site/common/stack/stack.scss @@ -0,0 +1,86 @@ +// +// Crafting Guide - stack.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__stack { + // using table-row display type to allow the quantity to always line up, even when the length is different + display : table-row; + max-width: 100%; + + & > * { + display : table-cell; + vertical-align : middle; + + &:not(:last-child) { + padding-bottom : $size-margin-xsmall; + } + } + + .quantity { + padding-right : $size-margin-medium; + text-align : right; + + input { + width: 4em; + + background : none; + border : none; + font-family : $font-family-text; + font-size : $font-size-large; + text-align : right; + } + } + + .icon { + padding-right : $size-margin-small; + + img { + height : $size-minecraft-block; + width : $size-minecraft-block; + } + } + + .name { + padding-right : $size-margin-large; + position: relative; + width: 100%; + + a { + // use absolute positioning to pull the name out of the layout so that a long name won't cause the row to + // be too long. Instead, this element will truncate itself with an ellipsis. + position: absolute; top: 50%; width: 100%; + transform: translateY(-50%); + + font-family : $font-family-text; + font-size : $font-size-medium; + line-height : $size-minecraft-block; + overflow : hidden; + text-overflow : ellipsis; + white-space : nowrap; + } + } + + .action { + padding-left : $size-margin-small; + + .button { + width : $size-button-height; + } + } +} + +// Editable //////////////////////////////////////////////////////////////////////////////////////////////////////////// + +.view__stack.editable { + .quantity { + input { + width : 3em; + + border-bottom : 1px dashed $color-gray-dark; + font-family : $font-family-input; + } + } +} diff --git a/src/client/site/common/stack/stack_controller.coffee b/src/client/site/common/stack/stack_controller.coffee new file mode 100644 index 000000000..600de9828 --- /dev/null +++ b/src/client/site/common/stack/stack_controller.coffee @@ -0,0 +1,180 @@ +# +# Crafting Guide - stack_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +BaseController = require '../../base_controller' + +######################################################################################################################## + +### +Events: + change(this) + change:quantity(this, oldQuantity, newQuantity) + button:first(this, type) + button:second(this, type) +### +module.exports = class StackController extends BaseController + + @::MAX_QUANTITY = 9999 + + constructor: (options={})-> + if not options.imageLoader? then throw new Error 'options.imageLoader is required' + if not options.model? then throw new Error 'options.model is required' + if not options.modPack? then throw new Error 'options.modPack is required' + if not options.router? then throw new Error 'options.router is required' + + options.templateName = 'common/stack' + super options + + @_editable = options.editable ?= false + @_firstButtonType = options.firstButtonType ?= null + @_imageLoader = options.imageLoader + @_modPack = options.modPack + @_secondButtonType = options.secondButtonType ?= null + @_shouldEnableButton = options.shouldEnableButton ?= (model, button)-> true + + @_modPack.on c.event.change, => @tryRefresh() + + # Event Methods ################################################################################ + + onFirstButtonClicked: (event)-> + @trigger c.event.button.first, this, @_firstButtonType + return false + + onQuantityFieldBlur: -> + return unless @_editable + + oldQuantity = @_priorValue + quantityText = @$quantityField.val().trim() + if quantityText.length is 0 + newQuantity = oldQuantity + else if not quantityText.match /^[0-9]*$/ + newQuantity = 1 + else + newQuantity = parseInt quantityText, 10 + if _.isNaN newQuantity then newQuantity = 1 + + newQuantity = Math.min newQuantity, @MAX_QUANTITY + newQuantity = Math.max 1, newQuantity + + @$quantityField.val "#{newQuantity}" + if newQuantity? and newQuantity isnt oldQuantity + @$quantityField.removeClass 'error' + @$quantityField.removeClass 'error-new' + + @model.quantity = newQuantity + @trigger c.event.change + ':quantity', this, oldQuantity, newQuantity + @trigger c.event.change, this + + onQuantityFieldChanged: -> + return unless @_editable + + quantityText = @$quantityField.val().trim() + if not quantityText.match /^[0-9]*$/ + @$quantityField.addClass 'error', 0 + @$quantityField.addClass 'error-new', 0 + @$quantityField.removeClass 'error-new' + else + @$quantityField.removeClass 'error' + @$quantityField.removeClass 'error-new' + + onQuantityFieldFocused: -> + if @_editable + @$quantityField.addClass 'editing' + @_priorValue = @model.quantity + @$quantityField.val '' + else + @$quantityField.blur() + + onQuantityKeyUp: (event)-> + return unless @_editable + + if event.which is c.key.return + @$quantityField.blur() + + onSecondButtonClicked: (event)-> + event.preventDefault() + @trigger c.event.button.second, this, @_secondButtonType + + # BaseController Overrides ##################################################################### + + onDidRender: -> + @$firstAction = @$('.action.first') + @$firstButton = @$('.action.first .button') + @$image = @$('.icon img') + @$nameLink = @$('.name a') + @$quantityField = @$('.quantity input') + @$secondAction = @$('.action.second') + @$secondButton = @$('.action.second .button') + super + + refresh: -> + if not @model? then throw new Error "must have a model to render" + + display = @_modPack.findItemDisplay @model.itemSlug + + @_imageLoader.load display.iconUrl, @$image + @$nameLink.html display.itemName + @$nameLink.attr 'href', display.itemUrl + + quantityText = if @model.quantity > 10000 then "#{@model.quantity / 1000}k" else "#{@model.quantity}" + @$quantityField.val quantityText + + @_refreshButtons() + + if @_editable + @$el.addClass 'editable' + @$quantityField.css 'width', '' + @$quantityField.removeAttr 'readonly' + else + @$el.removeClass 'editable' + @$quantityField.css 'width', "#{quantityText}".length * 0.66 + "em" + @$quantityField.attr 'readonly', 'readonly' + + super + + # Backbone.View Overrides ###################################################################### + + events: -> + return _.extend super, + 'blur .quantity input': 'onQuantityFieldBlur' + 'click .name a': 'routeLinkClick' + 'click .action.first .button': 'onFirstButtonClicked' + 'click .action.second .button': 'onSecondButtonClicked' + 'focus .quantity input': 'onQuantityFieldFocused' + 'input .quantity input': 'onQuantityFieldChanged' + 'keyup .quantity input': 'onQuantityKeyUp' + + # Private Methods ############################################################################## + + _refreshButtons: -> + @_updateButtonType @$firstButton, @_firstButtonType + @_updateButtonType @$secondButton, @_secondButtonType + + actions = [@$firstAction, @$secondAction] + buttons = [@$firstButton, @$secondButton] + + for buttonType, index in [@_firstButtonType, @_secondButtonType] + display = if @_shouldEnableButton(@model, index) then '' else 'none' + display = if not buttonType? then 'none' else display + actions[index].css 'display', display + + $label = buttons[index].find 'p' + switch buttonType + when 'check' then $label.text '✓' + when 'down' then $label.text '⬇︎' + when 'remove' then $label.text '-' + when 'up' then $label.text '⬆︎' + + _updateButtonType: ($button, type)-> + for currentType in ['check', 'down', 'remove', 'up'] + $button.removeClass currentType + + if type? + $button.css 'display', null + $button.addClass type + else + $button.css 'display', 'none' diff --git a/src/jade/templates/video.jade b/src/client/site/common/video/video.jade similarity index 53% rename from src/jade/templates/video.jade rename to src/client/site/common/video/video.jade index 8e1e8e72e..797100ee2 100644 --- a/src/jade/templates/video.jade +++ b/src/client/site/common/video/video.jade @@ -1,10 +1,10 @@ //- //- Crafting Guide - video.jade //- -//- Copyright (c) 2015 by Redwood Labs +//- Copyright © 2014-2016 by Redwood Labs //- All rights reserved. //- .view__video - iframe(width="365", height="273", src="", frameborder="0", allowfullscreen="true") + iframe(width="356", height="267", src="", frameborder="0", allowfullscreen="true") .caption: p \ No newline at end of file diff --git a/src/client/site/common/video/video.scss b/src/client/site/common/video/video.scss new file mode 100644 index 000000000..c6d1a5d84 --- /dev/null +++ b/src/client/site/common/video/video.scss @@ -0,0 +1,20 @@ +// +// Crafting Guide - video.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__video { + display: flex; + flex-direction: column; + align-items: center; + justify-content: center; + + .caption { + margin-top: $size-margin-small; + + font-family: $font-family-control; + font-size: $font-size-medium; + } +} diff --git a/src/coffee/controllers/video_controller.coffee b/src/client/site/common/video/video_controller.coffee similarity index 80% rename from src/coffee/controllers/video_controller.coffee rename to src/client/site/common/video/video_controller.coffee index 2cb9c044c..8c41cd8d5 100644 --- a/src/coffee/controllers/video_controller.coffee +++ b/src/client/site/common/video/video_controller.coffee @@ -1,11 +1,11 @@ -### -Crafting Guide - video_controller.coffee +# +# Crafting Guide - video_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' +BaseController = require '../../base_controller' ######################################################################################################################## @@ -13,7 +13,7 @@ module.exports = class VideoController extends BaseController constructor: (options={})-> if not options.model? then throw new Error 'options.model is required' - options.templateName = 'video' + options.templateName = 'common/video' super options # BaseController Overrides ##################################################################### diff --git a/src/client/site/craft_page/craft_page.jade b/src/client/site/craft_page/craft_page.jade new file mode 100644 index 000000000..9ab7647c6 --- /dev/null +++ b/src/client/site/craft_page/craft_page.jade @@ -0,0 +1,63 @@ +//- +//- Crafting Guide - craft_page.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +- var quarryHref = '/craft/quarry' +- var quarry +- var quantumSuitHref = '/craft/quantumsuit_bodyarmor:quantumsuit_boots:quantumsuit_helmet:quantumsuit_leggings' +- var ic2Href = '/browse/industrial_craft_2' +- var solarPanelHref = '/craft/solar_panel_vi' +- var solarFluxHref = '/browse/solar_flux' + +.content.view__craft_page + .left + .view__adsense + + .right + section.instructions + h2 Instructions + .panel + p. + Crafting Guide provides step-by-step instructions for thousands of items from Minecraft and many + popular mods. Just click "Add an item..." down below. + p. + Not sure what you'd like to make? Try one of these: + .items + a(href="/craft/potion_of_strength_ii_1_30") + img(src="/data/minecraft/items/potion_of_strength_ii_1_30/icon.png") + a(href="/craft/quarry") + img(src="/data/buildcraft/items/quarry/icon.png") + a(href="/craft/quantumsuit_bodyarmor:quantumsuit_boots:quantumsuit_helmet:quantumsuit_leggings") + img(src="/data/ic2_classic/items/quantumsuit_helmet/icon.png") + a(href="/craft/solar_panel_vi") + img(src="/data/solar_flux/items/solar_panel_vi/icon.png") + a(href="/craft/crystal_chest") + img(src="/data/iron_chests/items/crystal_chest/icon.png") + a(href="/craft/digital_miner") + img(src="/data/mekanism/items/digital_miner/icon.png") + a(href="/craft/2.tesseract") + img(src="/data/thermal_expansion/items/tesseract/icon.png") + + section.want + h2 Items to Make + .panel + .view__inventory.large.editable + + section.have + h2 Already in Inventory + .panel + .view__inventory.large.editable + + section.view__craftsman_working + + section.need + h2 Need to Gather + .panel + .view__inventory.large + + section.steps + h2 Steps + .panel \ No newline at end of file diff --git a/src/client/site/craft_page/craft_page.scss b/src/client/site/craft_page/craft_page.scss new file mode 100644 index 000000000..76e136f9d --- /dev/null +++ b/src/client/site/craft_page/craft_page.scss @@ -0,0 +1,52 @@ +// +// Crafting Guide - craft_page.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__craft_page { + @include layout-body-with-sidebar; + + .instructions { + .panel { + padding : $size-margin-large $size-margin-xlarge; + + p { + margin-bottom : $size-margin-large; + + font-family : $font-family-text; + font-size : $font-size-large; + line-height : $font-size-large * 1.5; + } + + .items { + display : flex; + flex-wrap : wrap; + justify-content : space-around; + margin-top : $size-margin-medium; + margin-right : -$size-margin-medium; + + a { + flex : 0 0 auto; + margin-top : $size-margin-medium; + margin-right : $size-margin-medium; + + background : $color-gray-faint; + border : 1px solid $color-gray-light; + padding : $size-margin-medium; + + img { + height : $size-minecraft-block * 1.5; + width : $size-minecraft-block * 1.5; + } + + &:hover { + background: $color-gray-light; + border-color: $color-gray-medium; + } + } + } + } + } +} diff --git a/src/coffee/controllers/craft_page_controller.coffee b/src/client/site/craft_page/craft_page_controller.coffee similarity index 52% rename from src/coffee/controllers/craft_page_controller.coffee rename to src/client/site/craft_page/craft_page_controller.coffee index d48372939..09e8c494d 100644 --- a/src/coffee/controllers/craft_page_controller.coffee +++ b/src/client/site/craft_page/craft_page_controller.coffee @@ -1,21 +1,18 @@ -### -Crafting Guide - craft_page_controller.coffee +# +# Crafting Guide - craft_page_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' -AdsenseController = require './adsense_controller' -CraftPage = require '../models/craft_page' -Craftsman = require '../models/crafting/craftsman' -CraftsmanWorkingController = require './craftsman_working_controller' -{Event} = require '../constants' -InventoryController = require './inventory_controller' -PageController = require './page_controller' -StepController = require './step_controller' -{Text} = require '../constants' -{Url} = require '../constants' +AdsenseController = require '../common/adsense/adsense_controller' +BaseController = require '../base_controller' +CraftPage = require '../../models/site/craft_page' +Craftsman = require '../../models/crafting/craftsman' +CraftsmanWorkingController = require './craftsman_working/craftsman_working_controller' +InventoryController = require '../common/inventory/inventory_controller' +PageController = require '../page_controller' +StepController = require './step/step_controller' ######################################################################################################################## @@ -24,24 +21,26 @@ module.exports = class CraftPageController extends PageController constructor: (options={})-> if not options.imageLoader? then throw new Error 'options.imageLoader is required' if not options.modPack? then throw new Error 'options.modPack is required' + if not options.router? then throw new Error 'options.router is required' if not options.storage? then throw new Error 'options.storage is required' options.model ?= new CraftPage modPack:options.modPack options.templateName = 'craft_page' super options - @imageLoader = options.imageLoader - @modPack = options.modPack - @storage = options.storage + @_imageLoader = options.imageLoader + @_modPack = options.modPack + @_router = options.router + @_storage = options.storage - # Event Methods ################################################################################ + # c.event Methods ################################################################################ onHaveInventoryChanged: -> logger.warning => "storing have: #{@model.craftsman.have.unparse()}" - @storage.store 'crafting-plan:have', @model.craftsman.have.unparse() + @_storage.store 'crafting-plan:have', @model.craftsman.have.unparse() onMoveNeedToHave: (itemSlug)-> - quantity = @needInventoryController.model.quantityOf itemSlug + quantity = @_needInventoryController.model.quantityOf itemSlug @model.craftsman.have.add itemSlug, quantity onRemoveFromHaveInventory: (itemSlug)-> @@ -49,11 +48,12 @@ module.exports = class CraftPageController extends PageController onRemoveFromWant: (itemSlug)-> @model.craftsman.want.remove itemSlug + @onWantInventoryChanged() onWantInventoryChanged: -> text = @model.craftsman.want.unparse() - url = Url.crafting inventoryText:text - router.navigate url + url = c.url.crafting inventoryText:text + @router.navigate url if @model.craftsman.want.isEmpty @model.craftsman.have.clear() @@ -61,7 +61,7 @@ module.exports = class CraftPageController extends PageController # PageController Overrides ##################################################################### getMetaDescription: -> - return Text.craftDescription() + return c.text.craftDescription() getTitle: -> return 'Craft' @@ -69,58 +69,61 @@ module.exports = class CraftPageController extends PageController # BaseController Overrides ##################################################################### onDidRender: -> - @adsenseController = @addChild AdsenseController, '.view__adsense', model:'sidebar_skyscraper' + @_adsenseController = @addChild AdsenseController, '.view__adsense', model:'skyscraper' - @wantInventoryController = @addChild InventoryController, '.want .view__inventory', - imageLoader: @imageLoader - isAcceptable: (item)=> item.isCraftable - model: @model.craftsman.want - modPack: @modPack + @_wantInventoryController = @addChild InventoryController, '.want .view__inventory', firstButtonType: 'remove' - @wantInventoryController.on Event.button.first, (c, s)=> @onRemoveFromWant(s) - @wantInventoryController.on Event.change, (c)=> @onWantInventoryChanged() + imageLoader: @_imageLoader + isAcceptable: (item)=> item.isCraftable + modPack: @_modPack + model: @model.craftsman.want + router: @_router + @_wantInventoryController.on c.event.button.first, (c, s)=> @onRemoveFromWant(s) + @_wantInventoryController.on c.event.change, (c)=> @onWantInventoryChanged() - @haveInventoryController = @addChild InventoryController, '.have .view__inventory', - imageLoader: @imageLoader - model: @model.craftsman.have - modPack: @modPack + @_haveInventoryController = @addChild InventoryController, '.have .view__inventory', firstButtonType: 'down' - @haveInventoryController.on Event.button.first, (controller, itemSlug)=> + imageLoader: @_imageLoader + modPack: @_modPack + model: @model.craftsman.have + router: @_router + @_haveInventoryController.on c.event.button.first, (controller, itemSlug)=> @onRemoveFromHaveInventory itemSlug - @haveInventoryController.on Event.change, (c)=> @onHaveInventoryChanged() + @_haveInventoryController.on c.event.change, (c)=> @onHaveInventoryChanged() - @needInventoryController = @addChild InventoryController, '.need .view__inventory', + @_needInventoryController = @addChild InventoryController, '.need .view__inventory', editable: false - imageLoader: @imageLoader - model: null - modPack: @modPack firstButtonType: 'up' - @needInventoryController.on Event.button.first, (c, s)=> @onMoveNeedToHave(s) + imageLoader: @_imageLoader + modPack: @_modPack + model: null + router: @_router + @_needInventoryController.on c.event.button.first, (c, s)=> @onMoveNeedToHave(s) - @workingSectionController = @addChild CraftsmanWorkingController, '.view__craftsman_working', + @_workingSectionController = @addChild CraftsmanWorkingController, '.view__craftsman_working', model: @model.craftsman - @$haveSection = @$('.have.section') - @$instructionsSection = @$('.instructions.section') - @$makeSection = @$('.make.section') - @$needSection = @$('.need.section') - @$stepsContainer = @$('.steps.section .panel') - @$stepsSection = @$('.steps.section') - @$toolsSection = @$('.tools.section') + @$haveSection = @$('section.have') + @$instructionsSection = @$('section.instructions') + @$makeSection = @$('section.make') + @$needSection = @$('section.need') + @$stepsContainer = @$('section.steps .panel') + @$stepsSection = @$('section.steps') + @$toolsSection = @$('section.tools') @$workingSection = @$('.view__craftsman_working') super onWillRender: -> @model.craftsman.have.clear() - @model.craftsman.have.parse @storage.load('crafting-plan:have') + @model.craftsman.have.parse @_storage.load('crafting-plan:have') super refresh: -> - @needInventoryController.model = @model.craftsman.plan?.need + @_needInventoryController.model = @model.craftsman.plan?.need @_refreshSectionVisibility() @_refreshSteps() - @adsenseController.fillAdPositions() + @_adsenseController.fillAdPositions() super # Backbone.View Overrides ######################################################################## @@ -160,24 +163,23 @@ module.exports = class CraftPageController extends PageController _refreshSectionVisibility: -> return unless @_rendered - toShow = [] - toHide = [] + allSections = [ + @$instructionsSection, @$haveSection, @$needSection, @$stepsSection, @$toolsSection, @$workingSection + ] + + visibleSections = [] if @model.craftsman.want.isEmpty - toShow.push el for el in [@$instructionsSection] - toHide.push el for el in [@$toolsSection, @$needSection, @$stepsSection, @$workingSection] + visibleSections.push el for el in [@$instructionsSection, @$wantSection] else if @model.craftsman.stage is Craftsman::STAGE.INVALID - toShow.push el for el in [@$workingSection] - toHide.push el for el in [@$instructionsSection, @$toolsSection, @$needSection, @$stepsSection] + visibleSections.push el for el in [@$wantSection, @$workingSection] else if not @model.craftsman.complete - toShow.push el for el in [@$workingSection] - toHide.push el for el in [@$instructionsSection, @$toolsSection, @$needSection, @$stepsSection] + visibleSections.push el for el in [@$wantSection, @$workingSection] else - toShow.push el for el in [@$toolsSection, @$needSection, @$stepsSection] - toHide.push el for el in [@$instructionsSection, @$workingSection] + visibleSections.push el for el in [@$haveSection, @$needSection, @$stepsSection, @$wantSection] - @show $el for $el in toShow - @hide $el for $el in toHide + @hide $el for $el in allSections + @show $el for $el in visibleSections _refreshSteps: -> steps = @model.craftsman.plan?.steps or [] @@ -192,9 +194,10 @@ module.exports = class CraftPageController extends PageController canComplete: (controller)=> @_isStepCompletable controller onComplete: (controller)=> @_completeStep controller onAddTools: (controller)=> @_addTools controller - imageLoader: @imageLoader + imageLoader: @_imageLoader model: step - modPack: @modPack + modPack: @_modPack + router: @_router controller.render() @$stepsContainer.append controller.$el diff --git a/src/jade/templates/craftsman_working.jade b/src/client/site/craft_page/craftsman_working/craftsman_working.jade similarity index 58% rename from src/jade/templates/craftsman_working.jade rename to src/client/site/craft_page/craftsman_working/craftsman_working.jade index bb7e65b40..4340f63d6 100644 --- a/src/jade/templates/craftsman_working.jade +++ b/src/client/site/craft_page/craftsman_working/craftsman_working.jade @@ -1,11 +1,11 @@ //- -//- Crafting Guide - item_group.jade +//- Crafting Guide - craftsman_working.jade //- -//- Copyright (c) 2015 by Redwood Labs +//- Copyright © 2014-2016 by Redwood Labs //- All rights reserved. //- -.view__item_group.section.hideable.hidden +.view__item_group.section .content .waiting img(src='/images/wait.gif') diff --git a/src/client/site/craft_page/craftsman_working/craftsman_working.scss b/src/client/site/craft_page/craftsman_working/craftsman_working.scss new file mode 100644 index 000000000..8ccc10cf3 --- /dev/null +++ b/src/client/site/craft_page/craftsman_working/craftsman_working.scss @@ -0,0 +1,38 @@ +/* +Crafting Table - crafting_table.scss + +Copyright (c) 2014-2015 by Redwood Labs +All rights reserved. +*/ + +.view__craftsman_working { + .content { + background: $color-white; + box-shadow: none; + + align-items : center; + display : flex; + flex-direction : column; + padding : $size-margin-xlarge; + + .waiting { + margin-bottom: $size-margin-xlarge; + } + + .message { + margin-bottom: $size-margin-medium; + + p { + font-family: $font-family-header; + font-size: $font-size-large; + } + } + + .count { + p { + font-family: $font-family-header; + font-size: $font-size-medium; + } + } + } +} diff --git a/src/coffee/controllers/craftsman_working_controller.coffee b/src/client/site/craft_page/craftsman_working/craftsman_working_controller.coffee similarity index 83% rename from src/coffee/controllers/craftsman_working_controller.coffee rename to src/client/site/craft_page/craftsman_working/craftsman_working_controller.coffee index cb3bd4701..cac9b0fb1 100644 --- a/src/coffee/controllers/craftsman_working_controller.coffee +++ b/src/client/site/craft_page/craftsman_working/craftsman_working_controller.coffee @@ -1,13 +1,12 @@ -### -Crafting Guide - crafting_grid_controller.coffee +# +# Crafting Guide - craftsman_working_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -Craftsman = require '../models/crafting/craftsman' -{Event} = require '../constants' +BaseController = require '../../base_controller' +Craftsman = require '../../../models/crafting/craftsman' ######################################################################################################################## @@ -15,10 +14,10 @@ module.exports = class CraftsmanWorkingController extends BaseController constructor: (options={})-> if not options.model then throw new Error 'options.model is required' - options.templateName = 'craftsman_working' + options.templateName = 'craft_page/craftsman_working' super options - @model.on Event.change, => @_refreshStatusText() + @model.on c.event.change, => @_refreshStatusText() # BaseController Methods ####################################################################### diff --git a/src/client/site/craft_page/step/step.jade b/src/client/site/craft_page/step/step.jade new file mode 100644 index 000000000..9c15b014e --- /dev/null +++ b/src/client/site/craft_page/step/step.jade @@ -0,0 +1,15 @@ +//- +//- Crafting Guide - step.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__step + h3 + .main_content + .view__inventory + .view__recipe + .buttons + .button.complete: .bezel: p complete step + .button.tool: .bezel: p make this tool diff --git a/src/client/site/craft_page/step/step.scss b/src/client/site/craft_page/step/step.scss new file mode 100644 index 000000000..d5fe5fb2a --- /dev/null +++ b/src/client/site/craft_page/step/step.scss @@ -0,0 +1,56 @@ +// +// Crafting Guide - step.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__step { + display: flex; + flex-direction: column; + + &:not(:first-child) { + border-top: 1px solid $color-gray-light; + margin-top: $size-margin-large; + padding-top: $size-margin-small; + } + + &:hover { + & > .buttons { + opacity: 1.0; + } + } + + h3 { + margin-bottom: 1em; + } + + .main_content { + display: flex; + + .view__inventory { + flex: 50%; + margin-left: $size-margin-large; + } + + .view__recipe { + flex: 50%; + } + } + + .buttons { + margin-top: $size-margin-large; + + opacity: 0; + + display: flex; + + .button { + flex: 1 1 50%; + + &:not(:first-child) { + margin-left: $size-margin-medium; + } + } + } +} \ No newline at end of file diff --git a/src/coffee/controllers/step_controller.coffee b/src/client/site/craft_page/step/step_controller.coffee similarity index 76% rename from src/coffee/controllers/step_controller.coffee rename to src/client/site/craft_page/step/step_controller.coffee index 947a8eba8..52efa6a05 100644 --- a/src/coffee/controllers/step_controller.coffee +++ b/src/client/site/craft_page/step/step_controller.coffee @@ -1,15 +1,13 @@ -### -Crafting Guide - step_controller.coffee +# +# Crafting Guide - step_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' -BaseController = require './base_controller' -{Event} = require '../constants' -InventoryController = require './inventory_controller' -MinimalRecipeController = require './minimal_recipe_controller' +BaseController = require '../../base_controller' +InventoryController = require '../../common/inventory/inventory_controller' +RecipeController = require '../../common/recipe/recipe_controller' ######################################################################################################################## @@ -19,15 +17,17 @@ module.exports = class StepController extends BaseController if not options.model? then throw new Error 'options.model is required' if not options.modPack? then throw new Error 'options.modPack is required' if not options.imageLoader? then throw new Error 'options.imageLoader is required' - options.templateName = 'step' + options.templateName = 'craft_page/step' super options + @_imageLoader = options.imageLoader + @_modPack = options.modPack + @_router = options.router + @canAddTools = options.canAddTools or (controller)-> true @canComplete = options.canComplete or (controller)-> true @onComplete = options.onComplete or (controller)-> # do nothing @onAddTools = options.onAddTools or (controller)-> # do nothing - @imageLoader = options.imageLoader - @modPack = options.modPack # Event Methods ################################################################################ @@ -44,14 +44,16 @@ module.exports = class StepController extends BaseController onDidRender: -> @inventoryController = @addChild InventoryController, '.view__inventory', editable: false - imageLoader: @imageLoader + imageLoader: @_imageLoader model: @model.inventory - modPack: @modPack + modPack: @_modPack + router: @_router - @recipeController = @addChild MinimalRecipeController, '.view__minimal_recipe', - imageLoader: @imageLoader + @recipeController = @addChild RecipeController, '.view__recipe', + imageLoader: @_imageLoader model: @model.recipe - modPack: @modPack + modPack: @_modPack + router: @_router @$completeButton = @$('.button.complete') @$header = @$('h3') @@ -64,7 +66,7 @@ module.exports = class StepController extends BaseController return super refresh: -> - itemDisplay = @modPack.findItemDisplay @model.recipe.output[0].itemSlug + itemDisplay = @_modPack.findItemDisplay @model.recipe.output[0].itemSlug @$header.html "#{@model.number}. #{itemDisplay.itemName}" @inventoryController.model = @model.inventory diff --git a/src/client/site/feedback/feedback.jade b/src/client/site/feedback/feedback.jade new file mode 100644 index 000000000..3e2264bf6 --- /dev/null +++ b/src/client/site/feedback/feedback.jade @@ -0,0 +1,19 @@ +//- +//- Crafting Guide - feedback.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__feedback + .form-content + input(name="name", placeholder="name (optional)") + input(name="email", placeholder="email (optional)") + + label(name="comment") Comment: + textarea(name="comment") + .error: p Sending failed. Please try again later. + .button.send: .bezel: p send + + .tab + p Feedback \ No newline at end of file diff --git a/src/client/site/feedback/feedback.scss b/src/client/site/feedback/feedback.scss new file mode 100644 index 000000000..1299c1d7a --- /dev/null +++ b/src/client/site/feedback/feedback.scss @@ -0,0 +1,88 @@ +// +// Crafting Guide - feedback.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__feedback { + min-height: $size-minecraft-block * 10; + z-index: $layer-dialog; + + background: white; + box-shadow: $size-margin-xxsmall $size-margin-xxsmall $size-margin-xsmall $color-shadow; + opacity: 0; + + display: flex; + + .form-content { + flex: 1 1 100%; + + border: $size-border-medium solid $color-black; + border-left: 0; + border-right: 0; + + display: flex; + flex-direction: column; + padding: $size-margin-medium; + + & > :not(:last-child) { + flex: 0 0 auto; + margin-bottom: $size-margin-medium; + } + + input { + display: block; + + font-family: $font-family-input; + font-size: $font-size-medium; + } + + label { + margin-top: $size-margin-small; + margin-bottom: $size-margin-small !important; + + font-family: $font-family-control; + font-size: $font-size-medium; + } + + textarea { + height: $font-size-medium * 10; + flex: 1 1 100%; + + border: $size-border-small solid $color-gray-light; + font-family: $font-family-input; + font-size: $font-size-medium; + resize: none; + } + + .error { + color: $color-error; + font-family: $font-family-control; + font-size: $font-size-small; + text-align: center; + } + } + + .tab { + $label-size: 25px; + + flex: 0 0 auto; + width: $label-size + 2 * $size-margin-medium; + + background: $color-gray-light; + border: $size-border-medium solid $color-black; + border-left: 0; + + display: flex; + align-items: center; + justify-content: center; + + p { + transform: rotate(-90deg); + + font-family: $font-family-header; + font-size: $label-size; + } + } +} diff --git a/src/coffee/controllers/feedback_controller.coffee b/src/client/site/feedback/feedback_controller.coffee similarity index 63% rename from src/coffee/controllers/feedback_controller.coffee rename to src/client/site/feedback/feedback_controller.coffee index 5eaef9ab3..1bb8d8210 100644 --- a/src/coffee/controllers/feedback_controller.coffee +++ b/src/client/site/feedback/feedback_controller.coffee @@ -1,17 +1,12 @@ -### -Crafting Guide - feedback_controller.coffee +# +# Crafting Guide - feedback_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' -BaseController = require './base_controller' -EmailClient = require '../models/email_client' -_ = require 'underscore' -w = require 'when' -{Duration} = require '../constants' -{Key} = require '../constants' +BaseController = require '../base_controller' +EmailClient = require '../../models/site/email_client' ######################################################################################################################## @@ -35,34 +30,28 @@ module.exports = class FeedbackController extends BaseController onSendClicked: -> return unless @$commentField.val().length > 0 - @$sendButton.attr 'disabled', 'disabled' + @$sendButton.addClass 'disabled' message = - subject:'Crafting Guide Feedback' - body: - """ - url: #{window.location.href} - name: #{@$nameField.val()} - email: #{@$emailField.val()} - comment: + url: window.location.href + name: @$nameField.val() + email: @$emailField.val() + comment: @$commentField.val() - #{@$commentField.val()} - """ - - @model.send(message) + @model.send('feedback', message) .then => @onToggle() - @$error.addClass 'hidden' + @$error.css display: 'none' .catch (error)=> - @$error.removeClass 'hidden' - .finally => - @$sendButton.removeAttr 'disabled' + @$error.css display: '' + .then => + @$sendButton.removeClass 'disabled' onTextChanged: (event)-> if @$commentField.val().length > 0 - @$sendButton.removeAttr 'disabled' + @$sendButton.removeClass 'disabled' else - @$sendButton.attr 'disabled', 'disabled' + @$sendButton.addClass 'disabled' onToggle: -> w.promise (resolve)=> @@ -70,15 +59,17 @@ module.exports = class FeedbackController extends BaseController if @isOpen @$screen.css display:'none' - @$el.animate {left:-@$el.outerWidth()}, duration:Duration.fast, complete:=> + @$page.removeClass 'blur' + @$el.animate {left:-@_closeWidth}, duration:c.duration.fast, complete:=> @$commentField.val '' @$('input, textarea').blur() resolve() else + @$page.addClass 'blur' @$screen.on 'click', => @onToggle() @$screen.css display:'block' - @$el.animate {left:0}, duration:Duration.fast, complete:=> + @$el.animate {left:0}, duration:c.duration.fast, complete:=> if @$nameField.val().length is 0 @$nameField.focus() else if @$emailField.val().length is 0 @@ -91,25 +82,31 @@ module.exports = class FeedbackController extends BaseController # BaseController Overrides ##################################################################### onDidRender: -> + @$page = $('.page') @$screen = $('.view__screen') @$commentField = @$('textarea[name="comment"]') @$emailField = @$('input[name="email"]') @$error = @$('.error') @$nameField = @$('input[name="name"]') - @$sendButton = @$('button[name="send"]') + @$sendButton = @$('.button.send') - windowHeight = window.innerHeight - @$el.delay(Duration.slow).animate {left:-@$el.outerWidth()}, Duration.normal + @$el.css left:-@$el.outerWidth() * 1.25, opacity: 1.0; + + @_closeWidth = @$el.outerWidth() - @$('.tab').outerWidth() + @$el.delay(c.duration.slow).animate {left:-@_closeWidth}, c.duration.normal @onTextChanged() + @$error.css display:'none' + @$sendButton.addClass 'disabled' + super # Backbone.View Methods ######################################################################## events: -> return _.extend super, - 'click .label': 'onToggle' - 'click button': 'onSendClicked' + 'click .tab': 'onToggle' + 'click .button': 'onSendClicked' 'input textarea': 'onTextChanged' 'keyup textarea': 'onTextChanged' diff --git a/src/client/site/footer/footer.jade b/src/client/site/footer/footer.jade new file mode 100644 index 000000000..aef3953c4 --- /dev/null +++ b/src/client/site/footer/footer.jade @@ -0,0 +1,42 @@ +//- +//- Crafting Guide - footer.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__footer + .divider.top + + .content + .left + h2 About + p. + Crafting Guide gives step-by-step instructions for making anything in Minecraft or its many mods. Just + say what you'd like to make, what you already have, it will do the rest, giving you a list of raw + materials and instructions of which items to make in the proper order. You can even ask it to include + the materials and instructions for all the tools you'll need along the way! + + .center + h2 Donate + p. + Crafting Guide is free for all, but if you find it helpful, donations in any amount are gratefully + accepted. + .action + form(action="https://www.paypal.com/cgi-bin/webscr", class="centered", method="post", target="_top") + input(type="hidden", name="cmd", value="_s-xclick") + input(type="hidden", name="hosted_button_id", value="GCB2TYZJYLAE6") + input(type="image", src="https://www.paypalobjects.com/en_US/i/btn/btn_donate_LG.gif", border="0", + name="submit" alt="PayPal - The safer, easier way to pay online!") + img(src="https://www.paypalobjects.com/en_US/i/scr/pixel.gif", width="1", height="1") + + .right + h2 Get Involved + p. + Crafting Guide is completely open-source, and you can help! Whether you want to write a recipe book + (all simple JSON), or implement new features, just head over to GitHub to get started. + .action + iframe(src="http://ghbtns.com/github-btn.html?user=andrewminer&repo=crafting-guide&type=fork&size=large", + allowtransparency="true", frameborder="0", scrolling="0", width="100", height="32") + + .divider.bottom diff --git a/src/client/site/footer/footer.scss b/src/client/site/footer/footer.scss new file mode 100644 index 000000000..364f7fd5c --- /dev/null +++ b/src/client/site/footer/footer.scss @@ -0,0 +1,57 @@ +// +// Crafting Guide - footer.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__footer { + display: flex; + flex-direction: column; + + background: $color-background-footer; + + .divider.top { + background: $color-dirt url('/images/grass_side.png'); + height: $size-minecraft-block; + } + + > .content { + display: flex; + + color: $color-text-light; + + .left, .center, .right { + flex: 1 1 33%; + margin: $size-margin-large $size-margin-large $size-margin-large 0; + + display: flex; + flex-direction: column; + + p { + font-family : $font-family-text; + font-size : $font-size-medium; + line-height : $font-size-medium * 1.25; + text-align : justify; + } + + .action { + flex: 1 1 auto; + align-self: center; + margin-bottom: $size-margin-large; + + display: flex; + align-items: flex-end; + } + + &:first-child { + margin-left: $size-margin-large; + } + } + } + + .divider.bottom { + background: $color-bedrock url('/images/bedrock.png'); + height: $size-minecraft-block; + } +} diff --git a/src/client/site/footer/footer_controller.coffee b/src/client/site/footer/footer_controller.coffee new file mode 100644 index 000000000..a1a39844f --- /dev/null +++ b/src/client/site/footer/footer_controller.coffee @@ -0,0 +1,16 @@ +# +# Crafting Guide - footer_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +BaseController = require '../base_controller' + +######################################################################################################################## + +module.exports = class FooterController extends BaseController + + constructor: (options={})-> + options.templateName = 'footer' + super options diff --git a/src/client/site/header/header.jade b/src/client/site/header/header.jade new file mode 100644 index 000000000..ebe30e327 --- /dev/null +++ b/src/client/site/header/header.jade @@ -0,0 +1,24 @@ +//- +//- Crafting Guide - header.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__header + .top-row + a.logo(href="/") + img(src="/images/site-icon.png") + + h1 Minecraft Crafting Guide + + .addthis_sharing_toolbox + + .divider + .button.craft: .bezel: p Craft + .button.browse: .bezel: p Browse + .button.news: .bezel: p News + .button.search: .bezel: p Search + .button.login: .bezel: p Login + + .breadcrumbs diff --git a/src/client/site/header/header.scss b/src/client/site/header/header.scss new file mode 100644 index 000000000..717c30491 --- /dev/null +++ b/src/client/site/header/header.scss @@ -0,0 +1,97 @@ +// +// Crafting Guide - header.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__header { + background: $color-gray-light; + + display : flex; + flex-direction : column; + + .top-row { + display : flex; + align-items : center; + + a { + flex : 0 0 auto; + height : $size-minecraft-block * 1.5; + width : $size-minecraft-block * 1.5; + margin-right : $size-margin-medium; + + img { + position : relative; + top : -$size-minecraft-block * 0.5; + left : -$size-minecraft-block * 0.5; + height : $size-minecraft-block * 2.0; + width : $size-minecraft-block * 2.0; + } + } + + h1 { + flex: 1 1 auto; + } + + .addthis_sharing_toolbox { + flex : 0 0 auto; + min-height : 37px; + min-width : 144px; + margin-right : $size-margin-small; + + + &.placeholder { + border : 1px solid orange; + text-align : center; + + &:before { + color : orange; + content : "ADD THIS"; + font-family : $font-family-header; + font-size : $font-size-large; + line-height : 37px; + } + } + } + } + + .divider { + background : $color-planks url('/images/planks.png'); + + align-items : center; + display : flex; + flex-wrap : wrap; + justify-content : space-around; + padding : $size-margin-medium $size-margin-medium; + padding-top : 0; + + .button { + flex : 1 1 20%; + min-width : 4 * $size-minecraft-block; + max-width : 5 * $size-minecraft-block; + margin-top: $size-margin-medium; + } + } + + .breadcrumbs { + background: $color-screen; + font-family: $font-family-control; + font-size: $font-size-medium; + + padding: $size-margin-small $size-margin-medium; + + &:before { + content: "⟩"; + margin-right: $size-margin-medium; + } + + a { + text-decoration: underline; + } + + span { + margin: 0 $size-margin-medium; + } + } +} diff --git a/src/client/site/header/header_controller.coffee b/src/client/site/header/header_controller.coffee new file mode 100644 index 000000000..00ef76129 --- /dev/null +++ b/src/client/site/header/header_controller.coffee @@ -0,0 +1,114 @@ +# +# Crafting Guide - header_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +BaseController = require '../base_controller' +ItemSelectorController = require '../common/item_selector/item_selector_controller' + +######################################################################################################################## + +module.exports = class HeaderController extends BaseController + + constructor: (options={})-> + if not options.modPack? then throw new Error 'options.modPack is required' + options.model ?= {} + options.templateName = 'header' + super options + + @_modPack = options.modPack + + global.site.on c.event.change + ':user', => @tryRefresh() + + # Event Methods ################################################################################ + + onCraft: -> + @router.navigate '/craft', trigger:true + return false + + onBrowse: -> + @router.navigate '/browse', trigger:true + return false + + onLogin: -> + if global.site.user? + global.site.logout() + else + @router.navigate '/login', trigger:true + return false + + onNews: -> + @router.navigate '/news', trigger:true + return false + + onSearch: -> + @_selector.launch() + .then (itemSlug)=> + itemDisplay = @_modPack.findItemDisplay itemSlug + @router.navigate itemDisplay.itemUrl, trigger:true + return false + + # BaseController Overrides ##################################################################### + + onDidRender: -> + @_selector = @addChild ItemSelectorController, null, modPack: @_modPack + + if global.env in c.productionEnvs + addThisUrl = 'http://s7.addthis.com/js/300/addthis_widget.js?pubid=ra-54f3c9717b2e530d' + $('body').append "" + else + @$('.addthis_sharing_toolbox').addClass 'placeholder' + + @$breadcrumbs = @$('.breadcrumbs') + @$loginButtonLabel = @$('.button.login p') + @$title = $('title') + super + + onWillChangeModel: (oldModel, newModel)-> + if oldModel? then @stopListening oldModel.controller + @listenTo newModel.controller, c.event.change, => @tryRefresh() + return newModel + + refresh: -> + @$loginButtonLabel.text if global.site.user? then "Logout" else "Login" + + @_refreshBreadcrumbs() + @_refreshTitle() + super + + # Backbone.View Overrides ###################################################################### + + events: -> + _.extend super, + 'click .craft': 'onCraft' + 'click .browse': 'onBrowse' + 'click .login': 'onLogin' + 'click .news': 'onNews' + 'click .search': 'onSearch' + 'click .breadcrumbs a': 'routeLinkClick' + + # Private Methods ############################################################################## + + _refreshBreadcrumbs: -> + breadcrumbs = @model?.controller?.getBreadcrumbs() + breadcrumbs ?= [] + + if breadcrumbs.length > 0 + @$breadcrumbs.empty() + + for crumb, index in breadcrumbs + if index isnt 0 then @$breadcrumbs.append $("") + @$breadcrumbs.append crumb + + @show @$breadcrumbs + else + @hide @$breadcrumbs + + _refreshTitle: -> + title = @model?.controller?.getTitle() + if title + @$title.text c.text.titleWithText text: title + else + @$title.text c.text.title() diff --git a/src/coffee/controllers/image_loader.coffee b/src/client/site/image_loader.coffee similarity index 95% rename from src/coffee/controllers/image_loader.coffee rename to src/client/site/image_loader.coffee index aa07ba877..9d99d69ef 100644 --- a/src/coffee/controllers/image_loader.coffee +++ b/src/client/site/image_loader.coffee @@ -1,11 +1,9 @@ -### -Crafting Guide - image_loader.coffee - -Copyright (c) 2014 by Redwood Labs -All rights reserved. -### - -{Duration} = require '../constants' +# +# Crafting Guide - image_loader.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# ######################################################################################################################## diff --git a/src/client/site/index.jade b/src/client/site/index.jade new file mode 100644 index 000000000..e31420a57 --- /dev/null +++ b/src/client/site/index.jade @@ -0,0 +1,35 @@ +//- +//- Crafting Guide - index.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +doctype html +html + head + title The Ultimate Minecraft Crafting Guide + link(href="/images/favicon.png" rel="icon" type="image/png") + link(href="/main.css" rel="stylesheet" type="text/css" ) + meta(charset="UTF-8") + meta(name="viewport" content="width=480") + + body + .view__feedback + .view__screen(style="display: none") + + .page + .view__header + + .content(style="display: none") + .content-loading + img(src="/images/wait.gif") + + .view__footer + + script(src="/external.js") + script(src="/internal.js") + + include ../includes/_google_adsense.jade + include ../includes/_google_analytics.jade + diff --git a/src/client/site/index.scss b/src/client/site/index.scss new file mode 100644 index 000000000..327278b4d --- /dev/null +++ b/src/client/site/index.scss @@ -0,0 +1,69 @@ +// +// Crafting Guide - index.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +html { + font-size : $size-rem; + + body { + background : $color-background-window url('/images/ice.png'); + width : 100%; + z-index : $layer-normal; + + display : flex; + justify-content : center; + + .view__feedback { + position: fixed; top: 50%; left: 0; width: $size-minecraft-block * 10; + transform: translateY(-50%); + } + + .view__screen { + position : fixed; top: 0; right: 0; bottom: 0; left: 0; + z-index : $layer-screen; + + background: $color-screen; + + display: flex; + align-items: center; + justify-content: center; + + & > :not(:first-child) { + display: none; + } + + & > *:first-child { + flex: 0 0 50%; + + box-shadow : $size-margin-small $size-margin-small $size-margin-large $color-shadow; + } + } + + .page { + margin : $size-margin-large 0; + max-width : $size-page-width; + width : 100%; + + background : $color-background-page; + box-shadow : $size-margin-small $size-margin-small $size-margin-large $color-shadow; + + display : flex; + flex-direction : column; + + > .content { + padding : $size-margin-medium; + } + + > .content-loading { + margin : $size-margin-xlarge 0; + + display : flex; + align-items : center; + justify-content : center; + } + } + } +} diff --git a/src/client/site/item_page/item_page.jade b/src/client/site/item_page/item_page.jade new file mode 100644 index 000000000..24f3a781a --- /dev/null +++ b/src/client/site/item_page/item_page.jade @@ -0,0 +1,44 @@ +//- +//- Crafting Guide - item_page.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.content.view__item_page + .left + .view__adsense + + .right + .about + .left + img + .center + .title + a.sourceMod + .button-row + .button.craftingPlan: .bezel: p View Crafting Plan + .right + p Official Link: + a.officialLink project page + + section.description.view__markdown_section + + section.multiblock + h2 Multiblock Construction + .panel + .view__multiblock_viewer + + section.recipes + h2 Recipes + .panel + + section.videos + h2 Videos + .panel + + section.view__item_group.usedToMake + + section.view__item_group.usedAsToolToMake + + section.view__item_group.similar \ No newline at end of file diff --git a/src/client/site/item_page/item_page.scss b/src/client/site/item_page/item_page.scss new file mode 100644 index 000000000..c4be18483 --- /dev/null +++ b/src/client/site/item_page/item_page.scss @@ -0,0 +1,60 @@ +// +// Crafting Guide - item_page.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__item_page { + @include layout-body-with-sidebar; + + .about { + margin-bottom: $size-margin-large; + display: flex; + + & > .left { + margin-right: $size-margin-large; + + flex: 0 0 auto; + + img { + height: $size-minecraft-block * 5; + width: $size-minecraft-block * 5; + } + } + + & > .center { + flex: 1 1 100%; + + display: flex; + flex-direction: column; + + .title { + font-family: $font-family-header; + font-size: $font-size-xxlarge; + } + + a.sourceMod { + font-family: $font-family-text; + font-size: $font-size-medium; + } + + .button-row { + flex: 1 1 100%; + + display: flex; + justify-content: center; + align-items: flex-end; + + .button { + flex: 1 1 100%; + max-width: 66%; + } + } + } + + & > .right { + flex: 0 0 auto; + } + } +} diff --git a/src/coffee/controllers/item_page_controller.coffee b/src/client/site/item_page/item_page_controller.coffee similarity index 57% rename from src/coffee/controllers/item_page_controller.coffee rename to src/client/site/item_page/item_page_controller.coffee index 6b33d6222..34157d61e 100644 --- a/src/coffee/controllers/item_page_controller.coffee +++ b/src/client/site/item_page/item_page_controller.coffee @@ -1,134 +1,145 @@ -### -Crafting Guide - item_page_controller.coffee +# +# Crafting Guide - item_page_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' -AdsenseController = require './adsense_controller' -{Duration} = require '../constants' -EditableFile = require '../models/editable_file' -{Event} = require '../constants' -FullRecipeController = require './full_recipe_controller' -{GitHub} = require '../constants' -ImageLoader = require './image_loader' -Item = require '../models/item' -ItemGroupController = require './item_group_controller' -ItemPage = require '../models/item_page' -ItemSlug = require '../models/item_slug' -MarkdownSectionController = require './markdown_section_controller' -MultiblockViewerController = require './multiblock_viewer_controller' -PageController = require './page_controller' -{Text} = require '../constants' -{Url} = require '../constants' -VideoController = require './video_controller' -w = require 'when' +AdsenseController = require '../common/adsense/adsense_controller' +EditableFile = require '../../models/site/editable_file' +Item = require '../../models/game/item' +ItemGroupController = require '../common/item_group/item_group_controller' +ItemPage = require '../../models/site/item_page' +ItemSlug = require '../../models/game/item_slug' +MarkdownSectionController = require '../common/markdown_section/markdown_section_controller' +MultiblockViewerController = require './multiblock_viewer/multiblock_viewer_controller' +PageController = require '../page_controller' +RecipeDetailController = require './recipe_detail/recipe_detail_controller' +VideoController = require '../common/video/video_controller' ######################################################################################################################## module.exports = class ItemPageController extends PageController - FILE_UPLOAD_DELAY = 250 + @::FILE_UPLOAD_DELAY = 250 constructor: (options={})-> if not options.client? then throw new Error 'options.client is required' if not options.itemSlug? then throw new Error 'options.itemSlug is required' if not options.imageLoader? then throw new Error 'options.imageLoader is required' if not options.modPack? then throw new Error 'options.modPack is required' + if not options.router? then throw new Error 'options.router is required' options.model ?= new ItemPage modPack:options.modPack options.templateName ?= 'item_page' super options - @client = options.client - @imageLoader = options.imageLoader - @modPack = options.modPack - + @_client = options.client @_descriptionFile = null - @_itemSlug = options.itemSlug + @_enterFeedback = options.enterFeedback + @_imageLoader = options.imageLoader + @_itemSlug = options.itemSlug + @_modPack = options.modPack + @_router = options.router - @modPack.on Event.change, => @tryRefresh() + @_modPack.on c.event.change, => + @tryRefresh() + @trigger c.event.change # Event Methods ################################################################################ craftingPlanButtonClicked: -> - display = @modPack.findItemDisplay @model.item.slug - router.navigate display.craftingUrl, trigger:true + display = @_modPack.findItemDisplay @model.item.slug + @_router.navigate display.craftingUrl, trigger:true return false # PageController Overrides ##################################################################### + getBreadcrumbs: -> + return [] unless @_itemSlug? + + display = @_modPack.findItemDisplay @_itemSlug + return [] unless display.itemName? and display.modName + + return [ + $("Browse") + $("#{display.modName}") + $("#{display.itemName}") + ] + getMetaDescription: -> - if @model.item? - display = @modPack.findItemDisplay @model.item.slug - return Text.itemDescription display - else - return null + return null unless @_itemSlug? + display = @_modPack.findItemDisplay @_itemSlug + return c.text.itemDescription display getTitle: -> - return unless @model.item? - display = @modPack.findItemDisplay @model.item.slug + return null unless @_itemSlug? + + display = @_modPack.findItemDisplay @_itemSlug + return null unless display.itemName? and display.modName? + return "#{display.itemName} from #{display.modName}" # BaseController Overrides ##################################################################### onDidRender: -> - @adsenseController = @addChild AdsenseController, '.view__adsense', model:'sidebar_skyscraper' + @_adsenseController = @addChild AdsenseController, '.view__adsense', model:'skyscraper', router: @_router - options = imageLoader:@imageLoader, modPack:@modPack, show:false + options = imageLoader:@_imageLoader, modPack:@_modPack, router:@_router, show:false @_multiblockController = @addChild MultiblockViewerController, '.view__multiblock_viewer', options @_similarItemsController = @addChild ItemGroupController, '.view__item_group.similar', options - @_usedAsToolToMakeController = @addChild ItemGroupController, '.view__item_group.usedAsToolToMake', options + @_usedAsToolToMakeController = @addChild ItemGroupController, '.view__item_group.usedAsToolToMake ', options @_usedToMakeController = @addChild ItemGroupController, '.view__item_group.usedToMake', options - @_descriptionController = @addChild MarkdownSectionController, '.section.description', - client: @client - editable: true - modPack: @modPack - beginEditing: => @_beginEditingDescription() - endEditing: => @_endEditingDescription() + @_descriptionController = @addChild MarkdownSectionController, '.view__markdown_section', + client: @_client + editable: true + modPack: @_modPack + router: @_router + beginEditing: => @_beginEditingDescription() + endEditing: => @_endEditingDescription() + enterFeedback: @_enterFeedback - @$byline = @$('.byline') - @$bylineLink = @$('.byline a') - @$descriptionSection = @$('.description') - @$multiblockSection = @$('.multiblock.section') - @$name = @$('h1.name') - @$officialPageLink = @$('a.officialPage') - @$recipeContainer = @$('.recipes .panel') - @$recipesSection = @$('.recipes') - @$recipesSectionTitle = @$('.recipes h2') - @$similarSection = @$('.similar') - @$titleImage = @$('.titleImage img') - @$usedAsToolToMakeSection = @$('.usedAsToolToMake') - @$usedToMakeSection = @$('.usedToMake') - @$videosContainer = @$('.videos .panel') - @$videosSection = @$('.videos') - @$videosSectionTitle = @$('.videos h2') + @$aboutImage = @$('.about img') + @$name = @$('.about .title') + @$officialLink = @$('.about a.officialLink') + @$sourceModLink = @$('.about a.sourceMod') + @$aboutLinks = @$('.about .right') + + @$multiblockSection = @$('section.multiblock') + @$recipeContainer = @$('section.recipes .panel') + @$recipesSection = @$('section.recipes') + @$recipesSectionTitle = @$('section.recipes h2') + @$similarSection = @$('section.similar') + @$usedAsToolToMakeSection = @$('section.usedAsToolToMake') + @$usedToMakeSection = @$('section.usedToMake') + @$videosContainer = @$('section.videos .panel') + @$videosSection = @$('section.videos') + @$videosSectionTitle = @$('section.videos h2') super refresh: -> @_resolveItemSlug() if @model.item? - display = @modPack.findItemDisplay @model.item.slug - @imageLoader.load display.iconUrl, @$titleImage - @$name.html display.itemName + display = @_modPack.findItemDisplay @model.item.slug + @_imageLoader.load display.iconUrl, @$aboutImage + @$name.text display.itemName - @_descriptionController.imageBase = Url.itemImageDir display + @_descriptionController.imageBase = c.url.itemImageDir display if @model.item.officialUrl? - @$officialPageLink.attr 'href', @model.item.officialUrl - @show @$officialPageLink + @$officialLink.attr 'href', @model.item.officialUrl + @show @$aboutLinks else - @hide @$officialPageLink + @hide @$aboutLinks @show() else @hide() - @_refreshByline() + @_refreshSourceMod() @_refreshDescription() @_refreshMultiblock() @_refreshRecipes() @@ -147,16 +158,16 @@ module.exports = class ItemPageController extends PageController events: -> return _.extend super, - 'click a.craftingPlan': 'routeLinkClick' - 'click .byline a': 'routeLinkClick' - 'click .markdown a': 'routeLinkClick' - 'click button.craftingPlan': 'craftingPlanButtonClicked' + 'click a.craftingPlan': 'routeLinkClick' + 'click a.sourceMod': 'routeLinkClick' + 'click .markdown a': 'routeLinkClick' + 'click .button.craftingPlan': 'craftingPlanButtonClicked' # Private Methods ############################################################################## _beginEditingDescription: -> - if not global.router.user? - global.router.login() + if not @user? + global.site.login() return w.reject new Error 'must be logged in to edit' if not @model.item? @@ -164,10 +175,10 @@ module.exports = class ItemPageController extends PageController pathArgs = modSlug:@_itemSlug.mod, itemSlug:@_itemSlug.item attributes = - fileName: GitHub.file.itemDescription.fileName pathArgs - path: GitHub.file.itemDescription.path pathArgs + fileName: c.gitHub.file.itemDescription.fileName pathArgs + path: c.gitHub.file.itemDescription.path pathArgs - @_descriptionFile = new EditableFile attributes, client:@client + @_descriptionFile = new EditableFile attributes, client:@_client @_descriptionFile.fetch() .then => if @_descriptionFile.encodedData?.length > 0 @@ -197,7 +208,7 @@ module.exports = class ItemPageController extends PageController return w(true) if fileList.length is 0 {file, message} = fileList.shift() file.save message - .delay FILE_UPLOAD_DELAY + .delay @FILE_UPLOAD_DELAY .then -> saveNextFile fileList @@ -206,16 +217,6 @@ module.exports = class ItemPageController extends PageController @model.item.description = oldDescription throw e - _refreshByline: -> - mod = @model.item?.modVersion?.mod - if mod?.name?.length > 0 - @$bylineLink.attr 'href', Url.mod modSlug:mod.slug - @$bylineLink.html mod.name - - @show @$byline - else - @hide @$byline - _refreshDescription: -> if @model.item?.description?.length > 0 @_descriptionController.model = @model.item.description @@ -239,7 +240,11 @@ module.exports = class ItemPageController extends PageController for recipe in @model.findRecipes() controller = @_recipeControllers[index] if not controller? - controller = new FullRecipeController imageLoader:@imageLoader, modPack:@modPack, model:recipe + controller = new RecipeDetailController + imageLoader: @_imageLoader + modPack: @_modPack + model: recipe + router: @_router @_recipeControllers.push controller @$recipeContainer.append controller.$el controller.render() @@ -262,6 +267,16 @@ module.exports = class ItemPageController extends PageController else @_similarItemsController.model = null + _refreshSourceMod: -> + mod = @model.item?.modVersion?.mod + if mod?.name?.length > 0 + @$sourceModLink.attr 'href', c.url.mod modSlug:mod.slug + @$sourceModLink.text mod.name + + @show @$sourceModLink + else + @hide @$sourceModLink + _refreshUsedAsToolToMake: -> @_usedAsToolToMakeController.title = 'Used as Tool to Make' @_usedAsToolToMakeController.model = @model.findToolForRecipes() @@ -299,12 +314,12 @@ module.exports = class ItemPageController extends PageController _resolveItemSlug: -> return if @model.item? - item = @modPack.findItem @_itemSlug, includeDisabled:true + item = @_modPack.findItem @_itemSlug, includeDisabled:true if item? if not ItemSlug.equal item.slug, @_itemSlug - router.navigate Url.item(modSlug:item.slug.mod, itemSlug:item.slug.item), trigger:true + router.navigate c.url.item(modSlug:item.slug.mod, itemSlug:item.slug.item), trigger:true return @model.item = item item.fetch() - item.on Event.sync, => @refresh() + item.on c.event.sync, => @refresh() diff --git a/src/jade/templates/multiblock.jade b/src/client/site/item_page/multiblock_viewer/multiblock/multiblock.jade similarity index 100% rename from src/jade/templates/multiblock.jade rename to src/client/site/item_page/multiblock_viewer/multiblock/multiblock.jade diff --git a/src/scss/templates/multiblock.scss b/src/client/site/item_page/multiblock_viewer/multiblock/multiblock.scss similarity index 65% rename from src/scss/templates/multiblock.scss rename to src/client/site/item_page/multiblock_viewer/multiblock/multiblock.scss index af46e1b66..8e0920c11 100644 --- a/src/scss/templates/multiblock.scss +++ b/src/client/site/item_page/multiblock_viewer/multiblock/multiblock.scss @@ -1,9 +1,12 @@ -/* -Crafting Guide - mod.scss +// +// Crafting Guide - multiblock.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ +$animate-slow: 400ms; +$animate-fast: 100ms; .view__multiblock { position: relative; diff --git a/src/coffee/controllers/multiblock_controller.coffee b/src/client/site/item_page/multiblock_viewer/multiblock/multiblock_controller.coffee similarity index 95% rename from src/coffee/controllers/multiblock_controller.coffee rename to src/client/site/item_page/multiblock_viewer/multiblock/multiblock_controller.coffee index 85c5beac7..914e230fb 100644 --- a/src/coffee/controllers/multiblock_controller.coffee +++ b/src/client/site/item_page/multiblock_viewer/multiblock/multiblock_controller.coffee @@ -5,9 +5,7 @@ Copyright (c) 2014-2015 by Redwood Labs All rights reserved. ### -$ = require 'jquery' -_ = require '../underscore_mixins' -BaseController = require './base_controller' +BaseController = require '../../../base_controller' ######################################################################################################################## @@ -29,7 +27,7 @@ module.exports = class MultiblockController extends BaseController constructor: (options={})-> if not options.imageLoader? then throw new Error 'options.imageLoader is required' if not options.modPack? then throw new Error 'options.modPack is required' - options.templateName = 'multiblock' + options.templateName = 'item_page/multiblock_viewer/multiblock' super options @_currentLayer = 0 @@ -69,7 +67,7 @@ module.exports = class MultiblockController extends BaseController super refresh: -> - @$el.css 'min-height':@_computeMinHeight(), 'min-width':@_computeMinWidth() + @$el.css 'height':@_computeMinHeight(), 'width':@_computeMinWidth() @_refreshBlockCache() @_refreshAllBlocks() diff --git a/src/jade/templates/multiblock_viewer.jade b/src/client/site/item_page/multiblock_viewer/multiblock_viewer.jade similarity index 82% rename from src/jade/templates/multiblock_viewer.jade rename to src/client/site/item_page/multiblock_viewer/multiblock_viewer.jade index d36ece823..167333041 100644 --- a/src/jade/templates/multiblock_viewer.jade +++ b/src/client/site/item_page/multiblock_viewer/multiblock_viewer.jade @@ -13,10 +13,10 @@ h3 Current Layer .view__inventory.layer .right + .buttons + .button.back: .bezel: p back + .button.next: .bezel: p next + .view__multiblock .caption img p   - .view__multiblock - .buttons - .button.back: p back - .button.next: p next diff --git a/src/client/site/item_page/multiblock_viewer/multiblock_viewer.scss b/src/client/site/item_page/multiblock_viewer/multiblock_viewer.scss new file mode 100644 index 000000000..911c8d2b9 --- /dev/null +++ b/src/client/site/item_page/multiblock_viewer/multiblock_viewer.scss @@ -0,0 +1,77 @@ +// +// Crafting Guide - multiblock_viewer.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__multiblock_viewer { + display: flex; + align-items: stretch; + + h3 { + margin-bottom: $size-margin-small; + margin-left: 0; + + &:not(:first-child) { + margin-top: $size-margin-large; + } + } + + .left { + border-right: 1px solid $color-gray-light; + flex: 1 0 40%; + + .view__inventory { + margin-left: $size-margin-medium; + } + } + + .right { + flex: 0 1 60%; + + display: flex; + flex-direction: column; + + .buttons { + flex: 0 0 auto; + margin-bottom: $size-margin-medium; + + display: flex; + justify-content: space-between; + + .button { + flex: 1 1 50%; + margin-left: $size-margin-medium; + } + } + + .view__multiblock { + flex: 0 0 auto; + align-self: center; + } + + .caption { + flex: 0 0 auto; + margin-top: $size-margin-medium; + + display: flex; + justify-content: center; + align-items: center; + + img { + margin-right : $size-margin-medium; + height : $size-minecraft-block; + width : $size-minecraft-block; + + + border : none; + } + + p { + font-family: $font-family-text; + font-size: $font-size-medium; + } + } + } +} diff --git a/src/coffee/controllers/multiblock_viewer_controller.coffee b/src/client/site/item_page/multiblock_viewer/multiblock_viewer_controller.coffee similarity index 83% rename from src/coffee/controllers/multiblock_viewer_controller.coffee rename to src/client/site/item_page/multiblock_viewer/multiblock_viewer_controller.coffee index 9744ac79d..15cb18154 100644 --- a/src/coffee/controllers/multiblock_viewer_controller.coffee +++ b/src/client/site/item_page/multiblock_viewer/multiblock_viewer_controller.coffee @@ -1,14 +1,13 @@ -### -Crafting Guide - multiblock_viewer_controller.coffee +# +# Crafting Guide - multiblock_viewer_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -_ = require '../underscore_mixins' -BaseController = require './base_controller' -InventoryController = require './inventory_controller' -MultiblockController = require './multiblock_controller' +BaseController = require '../../base_controller' +InventoryController = require '../../common/inventory/inventory_controller' +MultiblockController = require './multiblock/multiblock_controller' ######################################################################################################################## @@ -17,12 +16,14 @@ module.exports = class MultiblockViewerController extends BaseController constructor: (options={})-> if not options.imageLoader? then throw new Error 'options.imageLoader is required' if not options.modPack? then throw new Error 'options.modPack is required' - options.templateName = 'multiblock_viewer' + if not options.router? then throw new Error 'options.router is required' + options.templateName = 'item_page/multiblock_viewer' super options @_imageLoader = options.imageLoader @_modPack = options.modPack @_hoverTimer = null + @_router = options.router # Event Methods ################################################################################ @@ -51,11 +52,13 @@ module.exports = class MultiblockViewerController extends BaseController editable: false imageLoader: @_imageLoader modPack: @_modPack + router: @_router @layerInventoryController = @addChild InventoryController, '.view__inventory.layer', editable: false imageLoader: @_imageLoader modPack: @_modPack + router: @_router @multiblockController = @addChild MultiblockController, '.view__multiblock', imageLoader: @_imageLoader diff --git a/src/jade/templates/full_recipe.jade b/src/client/site/item_page/recipe_detail/recipe_detail.jade similarity index 53% rename from src/jade/templates/full_recipe.jade rename to src/client/site/item_page/recipe_detail/recipe_detail.jade index 67b0ba877..15a508c86 100644 --- a/src/jade/templates/full_recipe.jade +++ b/src/client/site/item_page/recipe_detail/recipe_detail.jade @@ -1,19 +1,18 @@ //- -//- Crafting Guide - full_recipe.jade +//- Crafting Guide - recipe_detail.jade //- -//- Copyright (c) 2015 by Redwood Labs +//- Copyright © 2014-2016 by Redwood Labs //- All rights reserved. //- -.view__full_recipe - +.view__recipe_detail .input h3 Ingredients .view__inventory .pattern - table.view__crafting_grid - .tool: a + .view__crafting_grid + a.tool .output h3 Produces diff --git a/src/client/site/item_page/recipe_detail/recipe_detail.scss b/src/client/site/item_page/recipe_detail/recipe_detail.scss new file mode 100644 index 000000000..17551d531 --- /dev/null +++ b/src/client/site/item_page/recipe_detail/recipe_detail.scss @@ -0,0 +1,44 @@ +// +// Crafting Guide - recipe_detail.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__recipe_detail { + display : flex; + + .input, .output{ + flex : 0 1 33%; + + h3 { + margin-bottom : 1em; + } + + .view__inventory { + margin-left: $size-margin-large; + } + } + + .pattern { + flex : 0 1 33%; + + display : flex; + flex-direction : column; + align-items : center; + + .tool { + margin-top : $size-margin-small; + + font-family : $font-family-text; + font-size : $font-size-medium; + text-align : center; + } + } + + &:not(:first-child) { + border-top : 1px solid $color-gray-light; + margin-top : $size-margin-medium; + padding-top : $size-margin-large; + } +} diff --git a/src/coffee/controllers/full_recipe_controller.coffee b/src/client/site/item_page/recipe_detail/recipe_detail_controller.coffee similarity index 61% rename from src/coffee/controllers/full_recipe_controller.coffee rename to src/client/site/item_page/recipe_detail/recipe_detail_controller.coffee index cdb17d144..e386a27b2 100644 --- a/src/coffee/controllers/full_recipe_controller.coffee +++ b/src/client/site/item_page/recipe_detail/recipe_detail_controller.coffee @@ -1,60 +1,65 @@ -### -Crafting Guide - full_recipe_controller.coffee +# +# Crafting Guide - recipe_detail_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -CraftingGridController = require './crafting_grid_controller' -ImageLoader = require './image_loader' -Inventory = require '../models/inventory' -InventoryController = require './inventory_controller' -_ = require 'underscore' -{Duration} = require '../constants' +BaseController = require '../../base_controller' +CraftingGridController = require '../../common/crafting_grid/crafting_grid_controller' +Inventory = require '../../../models/game/inventory' +InventoryController = require '../../common/inventory/inventory_controller' {StringBuilder} = require 'crafting-guide-common' ######################################################################################################################## -module.exports = class FullRecipeController extends BaseController +module.exports = class RecipeDetailController extends BaseController constructor: (options={})-> if not options.imageLoader? then throw new Error 'options.imageLoader is required' if not options.modPack? then throw new Error 'options.modPack is required' - options.templateName = 'full_recipe' + if not options.router? then throw new Error 'options.router is required' + options.templateName = 'item_page/recipe_detail' super options - @imageLoader = options.imageLoader - @modPack = options.modPack + @_imageLoader = options.imageLoader + @_modPack = options.modPack + @_router = options.router # BaseController Overrides ##################################################################### onDidRender: -> @gridController = @addChild CraftingGridController, '.view__crafting_grid', - imageLoader: @imageLoader - modPack: @modPack + imageLoader: @_imageLoader + modPack: @_modPack + router: @_router @inputController = @addChild InventoryController, '.input .view__inventory', editable: false - imageLoader: @imageLoader + imageLoader: @_imageLoader model: new Inventory - modPack: @modPack + modPack: @_modPack + router: @_router @outputController = @addChild InventoryController, '.output .view__inventory', editable: false - imageLoader: @imageLoader + imageLoader: @_imageLoader model: new Inventory - modPack: @modPack + modPack: @_modPack + router: @_router @$toolContainer = @$('.tool') super refresh: -> - @gridController.model = @model - - @_refreshInputs() - @_refreshOutputs() - @_refreshTools() + if @model? + @gridController.model = @model + @_refreshInputs() + @_refreshOutputs() + @_refreshTools() + @show() + else + @hide() super @@ -89,6 +94,6 @@ module.exports = class FullRecipeController extends BaseController builder = new StringBuilder builder.loop @model.tools, delimiter:', ', onEach:(b, stack)=> - display = @modPack.findItemDisplay stack.itemSlug + display = @_modPack.findItemDisplay stack.itemSlug b.push "#{display.itemName}" @$toolContainer.html builder.toString() diff --git a/src/client/site/login_page/login_page.jade b/src/client/site/login_page/login_page.jade new file mode 100644 index 000000000..bfc7d1ec2 --- /dev/null +++ b/src/client/site/login_page/login_page.jade @@ -0,0 +1,80 @@ +//- +//- Crafting Guide - login_page.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.content.view__login_page + .ready-to-login + .left + h1 Login with GitHub + p. + Use your GitHub credentials to login and make changes on Crafting Guide. No GitHub account? Don't + worry, you can get one for free. read more... + + .expandable-container.read-more + .content + p. + All changes you make on the site get submitted directly to our GitHub repo, and then published + through the same automated deployment process as changes made by anyone else. That way, anyone + can contribute easily: whether developer or end user. + p. + To log in, we redirect you to GitHub's site, and once you're signed in, they'll send you back + here. We never see your credentials, and only get the minimum set of permissions necessary to + submit changes to the Crafting Guide repo on your behalf. + p. + GitHub offers free accounts, so even if you don't already have one, you've got nothing to lose! + + .actions + .button.login: .bezel: p Login with GitHub + + .right + img(src="/images/github-login-large.png") + + .fetching-token + .left + h1 Completing log in... + p Hang on just a second while we finish logging you in... + .actions + img(src="/images/wait.gif") + .right + img(src="/images/github-login-large.png") + + .invalid-callback + .left + h1 Oops! + p. + Sorry about that, but it looks like something went wrong with your GitHub login. Click the button below + to try again, or use the Feedback button on the left to let us know, and we'll try to help. + + .actions + .button.login: .bezel: p Login with GitHub + .right + img(src="/images/github-login-large.png") + + .logged-in + .left + h1 All set! + p. + You are logged in to CraftingGuide using the following GitHub account: + .user + .left + img + .right + .name + .email + p.withRedirect. + You will be redirected shortly. + .actions + .button.logout: .bezel: p Logout + .right + img.float-right(src="/images/github-login-large.png") + + .server-down + .left + h1 Sorry! + p. + Our interactive editing service is down right now, but you can always submit a pull request over at the + Crafting Guide GitHub Repository. We'll + have the editing service back up soon! diff --git a/src/client/site/login_page/login_page.scss b/src/client/site/login_page/login_page.scss new file mode 100644 index 000000000..7c4001177 --- /dev/null +++ b/src/client/site/login_page/login_page.scss @@ -0,0 +1,89 @@ +// +// Crafting Guide - login_page.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__login_page { + display: flex; + align-items: center; + justify-content: center; + + & > div { + max-width: 75%; + + display: flex; + align-items: center; + + & > .left { + flex: 1 1 66%; + margin-right: $size-margin-large; + + display: flex; + flex-direction: column; + + p { + font-family: $font-family-text; + font-size: $font-size-medium; + line-height: $font-size-medium * 1.25; + + &:not(:first-child) { + margin-top: $size-margin-medium; + } + } + + .actions { + margin-top: $size-margin-large; + + padding: 0 $size-margin-xlarge; + + p { + font-family: $font-family-header; + font-size: 20px; + } + } + + .expandable-container { + margin-top: $size-margin-medium; + max-height: 0; + overflow: hidden; + transition: max-height 500ms; + } + + .user { + margin: $size-margin-large; + display: flex; + + @include floating-panel; + padding: $size-margin-medium; + + .left { + margin-right: $size-margin-small; + + img { + height: $size-minecraft-block * 2; + width: $size-minecraft-block * 2; + } + } + + .right { + .name { + font-family: $font-family-text; + font-size: $font-size-xlarge; + } + + .email { + font-family: $font-family-text; + font-size: $font-size-small; + margin-top: $size-margin-xsmall; + } + } + } + } + + & > .right { + flex: 0 0 33%; + } + } +} diff --git a/src/client/site/login_page/login_page_controller.coffee b/src/client/site/login_page/login_page_controller.coffee new file mode 100644 index 000000000..25d3da52d --- /dev/null +++ b/src/client/site/login_page/login_page_controller.coffee @@ -0,0 +1,144 @@ +# +# Crafting Guide - login_page_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +PageController = require '../page_controller' +GitHubUser = require '../../models/site/github_user' +{CraftingGuideClient} = require 'crafting-guide-common' + +######################################################################################################################## + +module.exports = class LoginPageController extends PageController + + @::State = + ReadyToLogin: 'ready-to-login' + ServerDown: 'server-down' + InvalidCallback: 'invalid-callback' + FetchingToken: 'fetching-token' + LoggedIn: 'logged-in' + + constructor: (options={})-> + options.templateName = 'login_page' + + @_client = options.client + @_params = options.params + @_storage = options.storage + + @_accessTokenLookupFailed = false + + @_client.on c.event.change + ':status', => @tryRefresh() + + super options + + # Event Methods ################################################################################ + + onExpandReadMore: (event)-> + @$readMoreLink.css display: 'none' + @$readMoreContainer.css 'max-height':@$readMoreContent.height() + return false + + onLoginButtonClicked: (event)-> + @_redirectToGitHub() + return false + + onLogoutButtonClicked: (event)-> + global.site.logout() + return false + + # Property Methods ############################################################################# + + getLoginSecurityToken: -> + @_storage.load 'loginSecurityToken' + + setLoginSecurityToken: (value)-> + @_storage.store 'loginSecurityToken', value + + Object.defineProperties @prototype, + loginSecurityToken: {get:@prototype.getLoginSecurityToken, set:@prototype.setLoginSecurityToken} + + # PageController Overrides ##################################################################### + + getTitle: -> + return "Login" + + # BaseController Methods ####################################################################### + + onDidRender: -> + @$readMoreContainer = @$('.expandable-container.read-more') + @$readMoreContent = @$('.read-more .content') + @$readMoreLink = @$('a.read-more') + @$redirectMessage = @$('.withRedirect') + @$userAvatar = @$('.user img') + @$userEmail = @$('.user .email') + @$userName = @$('.user .name') + + if (not @user?) and (@_params?.state?) and (@_params?.state is @loginSecurityToken) + @_client.completeGitHubLogin code:@_params.code + .then (response)=> + attributes = response.json.data.user + if attributes? + global.site.user = new GitHubUser attributes + global.site.resumeAfterLogin() + .catch (error)=> + logger.error "Failed to get access token: #{error}" + @_accessTokenLookupFailed = true + @refresh() + .done() + super + + refresh: -> + state = @_computeState() + @$el.find('> *').css display: 'none' + @$(".#{state}").css display: '' + + if state is @State.LoggedIn + @$userAvatar.attr 'src', @user.avatarUrl + @$userEmail.text @user.email + @$userName.text @user.name + + postLoginUrl = @_storage.load 'post-login-url' + @$redirectMessage.css display:(if postLoginUrl? then 'none' else '') + + super + + # Backbone.View Overrides ###################################################################### + + events: -> + return _.extend super, + 'click a.read-more': 'onExpandReadMore' + 'click .button.login': 'onLoginButtonClicked' + 'click .button.logout': 'onLogoutButtonClicked' + + # Private Methods ############################################################################## + + _computeState: -> + if @user? then return @State.LoggedIn + + if @_client.status is CraftingGuideClient.Status.Down then return @State.ServerDown + + if @_accessTokenLookupFailed then return @State.InvalidCallback + + if @_params?.state? + if @_params.state is @loginSecurityToken + return @State.FetchingToken + else + return @State.InvalidCallback + + return @State.ReadyToLogin + + _compeleteLogin: (code)-> + @_client.completeGitHubLogin code:code + .then (response)=> + global.site.user = new GitHubUser response.json + .catch (error)=> + @_accessTokenLookupFailed = true + @refresh() + .done() + + _redirectToGitHub: -> + @loginSecurityToken = _.uuid() + clientId = c.login.clientIds[global.env] + window.location.href = c.login.authorizeUrl clientId:clientId, state:@loginSecurityToken diff --git a/src/client/site/mod_page/mod_page.jade b/src/client/site/mod_page/mod_page.jade new file mode 100644 index 000000000..927f7bfe4 --- /dev/null +++ b/src/client/site/mod_page/mod_page.jade @@ -0,0 +1,36 @@ +//- +//- Crafting Guide - item_page.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.content.view__mod_page + .left + .view__adsense + + .right + .about + .left + img + .center + .title + .author + .description + .version + span in my mod pack + select + .warning. + PLEASE NOTE: By selecting "no", crafting plans, search, and other features will ignore items + and recipes from this mod. + .right + p Official Links: + a.homePage project page + a.documentation documentation + a.download download + + section.tutorials + h2 Tutorials + .panel + + .itemGroups diff --git a/src/client/site/mod_page/mod_page.scss b/src/client/site/mod_page/mod_page.scss new file mode 100644 index 000000000..42c1f76d1 --- /dev/null +++ b/src/client/site/mod_page/mod_page.scss @@ -0,0 +1,94 @@ +// +// Crafting Guide - item_page.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__mod_page { + @include layout-body-with-sidebar; + + .about { + margin-bottom: $size-margin-xlarge; + + display: flex; + + .left { + flex: 0 0 auto; + margin-right: $size-margin-large; + + img { + height: $size-minecraft-block * 5; + width: $size-minecraft-block * 5; + } + } + + .center { + flex: 1 1 100%; + margin-right: $size-margin-large; + + .title { + font-family: $font-family-header; + font-size: $font-size-xxlarge; + } + + .author { + font-family: $font-family-text; + font-size: $font-size-medium; + + &:before { + content: "by: " + } + } + + .description { + margin-top: $size-margin-large; + + font-family: $font-family-text; + font-size: $font-size-medium; + line-height: $font-size-medium * 1.25; + } + + .version { + margin-top: $size-margin-large; + + font-family: $font-family-control; + font-size: $font-size-medium; + + display: flex; + align-items: baseline; + + span { + flex: 0 0 auto; + + margin-right: $size-margin-medium; + } + + select { + flex: 1 1 100%; + + font-family: $font-family-control; + font-size: $font-size-medium; + } + } + + .warning { + margin-top: $size-margin-medium; + + color: $color-error; + font-family: $font-family-text; + font-size: $font-size-small; + line-height: $font-size-small * 1.25; + + b { + font-weight: bold; + } + } + } + + .right { + flex: 0 0 auto; + @include layout-link-list; + } + } +} \ No newline at end of file diff --git a/src/client/site/mod_page/mod_page_controller.coffee b/src/client/site/mod_page/mod_page_controller.coffee new file mode 100644 index 000000000..a766492e3 --- /dev/null +++ b/src/client/site/mod_page/mod_page_controller.coffee @@ -0,0 +1,184 @@ +# +# Crafting Guide - mod_page_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +AdsenseController = require '../common/adsense/adsense_controller' +BaseController = require '../base_controller' +Item = require '../../models/game/item' +ItemGroupController = require '../common/item_group/item_group_controller' +Mod = require '../../models/game/mod' +TutorialController = require './tutorial/tutorial_controller' + +######################################################################################################################## + +module.exports = class ModPageController extends BaseController + + constructor: (options={})-> + if not options.imageLoader? then throw new Error 'options.imageLoader is required' + if not options.modPack? then throw new Error 'options.modPack is required' + if not options.router? then throw new Error 'options.router is required' + options.templateName = 'mod_page' + super options + + @_imageLoader = options.imageLoader + @_modPack = options.modPack + @_router = options.router + + # Event Methods ################################################################################ + + onVersionChanged: -> + @model.activeVersion = @$versionSelector.val() + return false + + # Property Methods ############################################################################# + + Object.defineProperties @prototype, + + effectiveModVersion: + get: -> + modVersion = @model.activeModVersion + modVersion ?= @model.getModVersion Mod.Version.Latest + modVersion.fetch() if modVersion? + return modVersion + + # PageController Overrides ##################################################################### + + getBreadcrumbs: -> + return [ + $('Browse') + $("#{@model.name}") + ] + + getTitle: -> + return @model.name + + # BaseController Overrides ##################################################################### + + onDidRender: -> + @_adsenseController = @addChild AdsenseController, '.view__adsense', model: 'skyscraper' + + @$author = @$('.about .author') + @$description = @$('.about .description') + @$documentationLink = @$('.about .documentation') + @$downloadLink = @$('.about .download') + @$homePageLink = @$('.about .homePage') + @$itemGroups = @$(".itemGroups") + @$logo = @$('.about img') + @$title = @$('.about .title') + @$tutorialsContainer = @$('section.tutorials .panel') + @$tutorialsSection = @$('section.tutorials') + @$versionSelector = @$('.version select') + @$warning = @$('.warning') + super + + refresh: -> + @_refreshAboutBlock() + @_refreshItemGroups() + @_refreshTutorials() + @_refreshVersionSelector() + super + + # Backbone.View Overrides ###################################################################### + + events: -> + return _.extend super, + 'change .version select': 'onVersionChanged' + + # Private Methods ############################################################################## + + _refreshAboutBlock: -> + if @model? + @$author.text @model.author + @$description.text @model.description + @$documentationLink.attr 'href', @model.documentationUrl + @$downloadLink.attr 'href', @model.downloadUrl + @$homePageLink.attr 'href', @model.homePageUrl + @$logo.attr 'src', c.url.modIcon modSlug:@model.slug + @$title.text @model.name + else + @$author.text '' + @$description.text '' + @$documentationLink.attr 'href', '' + @$downloadLink.attr 'href', '' + @$homePageLink.attr 'href', '' + @$logo.attr 'src', '' + @$title.text '' + + _refreshItemGroups: -> + @_groupControllers ?= [] + groupIndex = 0 + modVersion = @effectiveModVersion + + if modVersion? + modVersion.eachGroup (group)=> + controller = @_groupControllers[groupIndex] + items = modVersion.allItemsInGroup group + if not controller? + controller = new ItemGroupController + imageLoader: @_imageLoader + model: items + modPack: @_modPack + router: @_router + title: if group is Item.Group.Other then 'Items' else group + + @_groupControllers.push controller + @$itemGroups.append controller.$el + controller.render() + else + controller.modVersion = modVersion + controller.model = items + controller.refresh() + groupIndex++ + + while @_groupControllers.length > groupIndex + 1 + @_groupControllers.pop().remove() + + _refreshTutorials: -> + @_tutorialControllers ?= [] + index = 0 + tutorials = @model.tutorials + + if tutorials.length > 0 + for tutorial in tutorials + controller = @_tutorialControllers[index] + if not controller? + controller = new TutorialController model: tutorial, router: @_router + @_tutorialControllers.push controller + @$tutorialsContainer.append controller.$el + controller.render() + else + controller.model = tutorial + + index += 1 + + while @_tutorialControllers.length > index + @_tutorialControllers.pop().remove() + + @show @$tutorialsSection + else + @hide @$tutorialsSection + + _refreshVersionSelector: -> + modVersions = @model.modVersions + selectedModVersion = @effectiveModVersion + + @$versionSelector.empty() + + $option = $("") + if not @model.enabled + @$warning.css display:'' + selectedModVersion = null + $option.attr 'selected', true + else + @$warning.css display:'none' + @$versionSelector.append $option + + for modVersion in @model.modVersions + $option = $("") + if modVersion is selectedModVersion + $option.attr 'selected', 'true' + @$versionSelector.append $option + @$versionSelector.css display:'' diff --git a/src/jade/templates/tutorial.jade b/src/client/site/mod_page/tutorial/tutorial.jade similarity index 64% rename from src/jade/templates/tutorial.jade rename to src/client/site/mod_page/tutorial/tutorial.jade index 2ab96ca96..1e926fe51 100644 --- a/src/jade/templates/tutorial.jade +++ b/src/client/site/mod_page/tutorial/tutorial.jade @@ -1,11 +1,11 @@ //- //- Crafting Guide - tutorial.jade //- -//- Copyright (c) 2015 by Redwood Labs +//- Copyright © 2014-2016 by Redwood Labs //- All rights reserved. //- .view__tutorial a img - .caption: p \ No newline at end of file + p diff --git a/src/client/site/mod_page/tutorial/tutorial.scss b/src/client/site/mod_page/tutorial/tutorial.scss new file mode 100644 index 000000000..91bd47610 --- /dev/null +++ b/src/client/site/mod_page/tutorial/tutorial.scss @@ -0,0 +1,30 @@ +// +// Crafting Guide - tutorial.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__tutorial { + display: flex; + flex-wrap: wrap; + + a { + flex: 0 0 auto; + + display: flex; + flex-direction: column; + align-items: center; + + img { + height: $size-minecraft-block * 4; + margin-bottom: $size-margin-xsmall; + width: $size-minecraft-block * 4; + } + + p { + font-family: $font-family-text; + font-size: $font-size-medium; + } + } +} diff --git a/src/coffee/controllers/tutorial_controller.coffee b/src/client/site/mod_page/tutorial/tutorial_controller.coffee similarity index 69% rename from src/coffee/controllers/tutorial_controller.coffee rename to src/client/site/mod_page/tutorial/tutorial_controller.coffee index 1451e1bd3..583ce6a5e 100644 --- a/src/coffee/controllers/tutorial_controller.coffee +++ b/src/client/site/mod_page/tutorial/tutorial_controller.coffee @@ -1,13 +1,11 @@ -### -Crafting Guide - tutorial_controller.coffee +# +# Crafting Guide - tutorial_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -_ = require 'underscore' -{Url} = require '../constants' +BaseController = require '../../base_controller' ######################################################################################################################## @@ -15,7 +13,7 @@ module.exports = class TutorialController extends BaseController constructor: (options={})-> if not options.model? then throw new Error 'options.model is required' - options.templateName = 'tutorial' + options.templateName = 'mod_page/tutorial' super options # BaseController Overrides ##################################################################### @@ -28,8 +26,8 @@ module.exports = class TutorialController extends BaseController refresh: -> templateData = modSlug:@model.modSlug, tutorialSlug:@model.slug - @$icon.attr 'src', Url.tutorialIcon templateData - @$link.attr 'href', Url.tutorial templateData + @$icon.attr 'src', c.url.tutorialIcon templateData + @$link.attr 'href', c.url.tutorial templateData @$title.html @model.name super diff --git a/src/client/site/news_page/news_page.jade b/src/client/site/news_page/news_page.jade new file mode 100644 index 000000000..373b9961a --- /dev/null +++ b/src/client/site/news_page/news_page.jade @@ -0,0 +1,162 @@ +//- +//- Crafting Guide - news_page.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.content.view__news_page + .left + .view__adsense + + .right + section + h3 2015-02-11 + .panel + p. + I've been using Modular PowerSuits myself lately, and I + noticed that the newest version (finally!) comes with default recipes. So, I've updated + Crafting Guide to support both the newest vanilla recipes as well as those from Thermal + Expansion. You can switch back and forth on the Configure page. + + section + h3 2015-02-09 + .panel + p. + Back before the winter holidays, the extremely patient + tdallmann completed support for Hydraulicraft, and I'm + afraid I'm only now getting it up on the site! It looks like a neat mod based all around the + science of hydraulics with a nicely stepped set of devices to be made at each level. Many thanks + to tddallmann for adding it to Crafting Guide! + p. + I also received a submission for adding OpenComputers from + yut23. Should be a big help to those aspiring Minecraft + programmers who want a bit more challege than is provided by + ComputerCraft! Thanks, yut23! + + section + h3 2015-11-25 + .panel + p. + With many thanks to Mike Caron, I'm pleased to announce + support for Storage Drawers! + + section + h3 2015-12-13 + .panel + p. + I'm super excited to announce that I've added full multi-block support for Crafting Guide! For + example, check out a 5-Core Reactor + from Big Reactors, or the 5x5x5 Steel Tank from + Railcraft. I'm really pleased with how it turned out! + + section + h3 2015-11-17 + .panel + p. + And today, it's Extra Cells! + + section + h3 2015-11-16 + .panel + p. + It's a small one, but also highly requested... Here's ComputerCraft! + + section + h3 2015-11-14 + .panel + p. + One more small one over the weekend... Advanced Solar + Panels has been added to crafting guide! + + section + h3 2015-11-14 + .panel + p. + For a long while now, Galacticraft has been the most + requested mod, and it's finally here! Enjoy! + + section + h3 2015-11-10 + .panel + p. + Remember me? They guy who runs the site. Yeah, I'm back, and with big news! The site now has + a completely new crafting algorithm. Instead of just taking the first crafting plan it comes up + with, it tries to compute every possible plan, rates them, and then picks the best one. This + also clears up a lot of bugs related to the old algorithm. The one drawback is that some items + can take a bit longer to compute than with the old way, but I think you'll find it's worth it! + p. + On a personal note, I think it's clear that I don't have nearly as much time to dedicate to the + site as I used to. That's mostly because I started a new job which keeps me away from working + on the site so much. I hope to be able to get into a more regular pace now things my personal + life has settled down again. + + section + h3 2015-07-25 + .panel + p. + You may have noticed things have been very quiet with the site for the past month... well I'm + afraid that's because I haven't been working on it. Instead, I've been hunting for a new job. + Now that I've got that all squared away (I'll be starting at Looker in Santa Cruz on Monday), + I'll have nights and weekends to continue working on the site. Thanks for being patient! + + section + h3 2015-06-12 + .panel + p. + Today I launched the second major part of the item description editor: image uploads! As you + enter your description, use the markdown notation for an image ![](image.png) and a + empty image preview will show up underneath the editor. Click the button to select an image from + your computer. Just be sure to keep the images to a reasonable size (< 750kB, and < 740px by + 600px). + + section + h3 2015-05-13 + .panel + p. + As of today, you can now add and edit item descriptions right on Crafting Guide. This feature is + starting small with just item descriptions, but eventually all the content on the site will be + editable. All you need is a (free) GitHub account, and you're ready to go! + p. + For those more comfortable with a regular text editor, all the content is still in GitHub under + the crafting-guide-data repo. + Just follow the instructions, and you can submit content via pull request instead of using the + website's editor. + + section + h3 2015-04-30 + .panel + p. + I've been working on a big new feature for a while now, but I didn't want to leave everyone + without anything new for so long... So, I've just finished adding MineFactory Reloaded! Enjoy! + + section + h3 2015-04-20 + .panel + p. + Okay... big changes on the crafting page! Instead of having four little boxes for the various + parts of the crafting plan, the new page shows all the steps as one long list. In addition, you + get a lot more control over the plan. Now, you can even mark individual steps as complete to get + a new crafting plan which doesn't include those items. + p. + As an example, let's say you're thinking about upgrading your Reinforced Jetpack to a shiny new Resonant Jetpack, you can just mark off the + step for the Reinforced Jetpack, and get only the materials and steps for doing the upgrade. + I'm really pleased with the new crafting page, and I think you're going to love it! + + section + h3 2015-04-11 + .panel + p. + I've just finished adding Simply Jetpacks by Tonius. It + seems like a simple mod on the surface, but what with all the upgrades and technology tiers, it + takes an amazing 87 steps to make the highest-tier + jetpack! + p. + I've also added Solar Flux by Nauktis. Again, another + deceptively simple mod, but the most powerful solar + panel kicks out an impressive 4096 RF/t! I just hope your mine has been productive... among + other things, you'll need 45 Diamonds, 110 Gold Ore, 1568 Copper Ore, and 6023 Iron Ore! diff --git a/src/client/site/news_page/news_page.scss b/src/client/site/news_page/news_page.scss new file mode 100644 index 000000000..dd31869ce --- /dev/null +++ b/src/client/site/news_page/news_page.scss @@ -0,0 +1,30 @@ +// +// Crafting Guide - news_page.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__news_page { + @include layout-body-with-sidebar; + + section { + &:not(:first-child) { + margin-top : $size-margin-large; + } + + h3 { + margin-bottom : $size-margin-small; + } + + p { + font-family : $font-family-text; + font-size : $font-size-medium; + line-height : $font-size-medium * 1.5; + + &:not(:last-child) { + margin-bottom : $size-margin-medium; + } + } + } +} diff --git a/src/client/site/news_page/news_page_controller.coffee b/src/client/site/news_page/news_page_controller.coffee new file mode 100644 index 000000000..170af6c5f --- /dev/null +++ b/src/client/site/news_page/news_page_controller.coffee @@ -0,0 +1,33 @@ +# +# Crafting Guide - news_page_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +AdsenseController = require '../common/adsense/adsense_controller' +PageController = require '../page_controller' + +######################################################################################################################## + +module.exports = class NewsPageController extends PageController + + constructor: (options={})-> + options.templateName = 'news_page' + super options + + # PageController Overrides ##################################################################### + + getTitle: -> + return "News" + + # BaseController Overrides ##################################################################### + + onDidRender: -> + @_adsenseController = @addChild AdsenseController, '.view__adsense', model:'skyscraper' + + # Backbone.View Overrides ###################################################################### + + events: -> + _.extend super, + 'click a': 'routeLinkClick' diff --git a/src/coffee/controllers/page_controller.coffee b/src/client/site/page_controller.coffee similarity index 83% rename from src/coffee/controllers/page_controller.coffee rename to src/client/site/page_controller.coffee index 3269e4895..7dea8aa73 100644 --- a/src/coffee/controllers/page_controller.coffee +++ b/src/client/site/page_controller.coffee @@ -1,13 +1,11 @@ -### -Crafting Guide - page_controller.coffee +# +# Crafting Guide - page_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' BaseController = require './base_controller' -{Text} = require '../constants' ######################################################################################################################## @@ -18,6 +16,9 @@ module.exports = class PageController extends BaseController # Public Methods ############################################################################### + getBreadcrumbs: -> + return [] + getMetaDescription: -> # subclasses should override this to return the page-specific text for the meta description tag return null @@ -48,6 +49,6 @@ module.exports = class PageController extends BaseController title = if title? then title.trim() else '' if title.length > 0 - $('title').html Text.titleWithText text:title + $('title').html c.text.titleWithText text:title else - $('title').html Text.title() + $('title').html c.text.title() diff --git a/src/client/site/router.coffee b/src/client/site/router.coffee new file mode 100644 index 000000000..7af9b39c3 --- /dev/null +++ b/src/client/site/router.coffee @@ -0,0 +1,169 @@ +# +# Crafting Guide - router.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +BrowsePageController = require './browse_page/browse_page_controller' +CraftPageController = require './craft_page/craft_page_controller' +ItemPageController = require './item_page/item_page_controller' +ItemSlug = require '../models/game/item_slug' +LoginPageController = require './login_page/login_page_controller' +ModPageController = require './mod_page/mod_page_controller' +NewsPageController = require './news_page/news_page_controller' +TutorialPageController = require './tutorial_page/tutorial_page_controller' +UrlParams = require './url_params' + +######################################################################################################################## + +module.exports = class Router extends Backbone.Router + + constructor: (siteController, options={})-> + if not siteController? then throw new Error "siteController is required" + + @_siteController = siteController + @_lastReported = null + + super options + + # Backbone.Router Overrides #################################################################### + + navigate: -> + super + @_recordPageView() + + routes: + '': 'route__home' + '/': 'route__home' + '/index.html': 'route__home' + + 'browse': 'route__browse' + 'browse/': 'route__browse' + 'browse/index.html': 'route__browse' + + 'browse/:modSlug': 'route__browseMod' + 'browse/:modSlug/': 'route__browseMod' + 'browse/:modSlug/index.html': 'route__browseMod' + + 'browse/:modSlug/:itemSlug': 'route__browseModItem' + 'browse/:modSlug/:itemSlug/': 'route__browseModItem' + 'browse/:modSlug/:itemSlug/index.html': 'route__browseModItem' + + 'browse/:modSlug/tutorials/:tutorialSlug': 'route__browseTutorial' + 'browse/:modSlug/tutorials/:tutorialSlug/': 'route__browseTutorial' + 'browse/:modSlug/tutorials/:tutorialSlug/index.html': 'route__browseTutorial' + + 'configure': 'route__configure' + 'configure/': 'route__configure' + 'configure/index.html': 'route__configure' + + 'craft': 'route__craft' + 'craft/': 'route__craft' + 'craft/index.html': 'route__craft' + + 'craft/:text': 'route__craft' + 'craft/:text/': 'route__craft' + 'craft/:text/index.html': 'route__craft' + + 'login': 'route__login' + 'login/': 'route__login' + 'login/index.html': 'route__login' + + 'news': 'route__news' + 'news/': 'route__news' + 'news/index.html': 'route__news' + + 'item/:itemSlug': 'deprecated__item' + 'crafting/(:text)': 'deprecated__crafting' + 'mod/:modSlug': 'deprecated__mod' + 'mod/:modSlug/:itemSlug': 'deprecated__modItem' + + # Route Methods ################################################################################ + + route__home: -> + params = new UrlParams recipeName:{type:'string'}, count:{type:'integer'} + if params.recipeName? + @deprecated__v1_root params + return + + @route__craft() + + route__browse: -> + @_siteController.setPage 'browse', new BrowsePageController @_makeOptions {} + + route__browseMod: (modSlug)-> + controller = new ModPageController @_makeOptions() + controller.model = @_siteController.modPack.getMod modSlug + @_siteController.setPage 'browseMod', controller + + route__browseModItem: (modSlug, itemSlug)-> + slug = new ItemSlug modSlug, itemSlug + controller = new ItemPageController @_makeOptions {itemSlug:slug} + @_siteController.setPage 'browseModItem', controller + + route__browseTutorial: (modSlug, tutorialSlug)-> + controller = new TutorialPageController @_makeOptions {modSlug:modSlug, tutorialSlug:tutorialSlug} + @_siteController.setPage 'browseTutorial', controller + + route__configure: -> + @route__craft() + + route__craft: (text)-> + controller = new CraftPageController @_makeOptions {} + controller.model.params = inventoryText:text + @_siteController.setPage 'craft', controller + + route__login: -> + params = new UrlParams code:{type:'string'}, state:{type:'string'} + controller = new LoginPageController @_makeOptions {params:params} + @_siteController.setPage 'login', controller + + route__news: -> + controller = new NewsPageController @_makeOptions {} + @_siteController.setPage 'news', controller + + # Deprecated Route Methods ##################################################################### + + deprecated__crafting: (text)-> + controller = new CraftPageController @_makeOptions {} + controller.model.params = inventoryText:text + @_siteController.setPage 'crafting', controller + + deprecated__item: (itemSlug)-> + controller = new ItemPageController @_makeOptions {itemSlug:ItemSlug.slugify(itemSlug)} + @_siteController.setPage 'item', controller + + deprecated__modItem: (modSlug, itemSlug)-> + slug = new ItemSlug modSlug, itemSlug + controller = new ItemPageController @_makeOptions {itemSlug:slug} + @_siteController.setPage 'item', controller + + deprecated__mod: (modSlug)-> + controller = new ModPageController @_makeOptions {} + controller.model = @_siteController.modPack.getMod modSlug + @_siteController.setPage 'mod', controller + + deprecated__v1_root: (params)-> + text = '' + if params.recipeName? + if params.count? and params.count > 1 + text = "#{params.count}.#{_.slugify(params.recipeName)}" + else + text = _.slugify params.recipeName + + @navigate c.url.crafting(inventoryText:text), trigger:true + + # Private Methods ############################################################################## + + _makeOptions: (options={})-> + return _.extend options, @_siteController.controllerOptions + + _recordPageView: -> + pathname = window.location.pathname + + if global.env is 'production' and ga? + logger.info -> "Recording GA page view: #{pathname}" + ga 'send', 'pageview', pathname + else + logger.info -> "Suppressing GA page view: #{pathname}" diff --git a/src/client/site/site_controller.coffee b/src/client/site/site_controller.coffee new file mode 100644 index 000000000..40e5909ca --- /dev/null +++ b/src/client/site/site_controller.coffee @@ -0,0 +1,163 @@ +# +# Crafting Guide - site_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +BaseController = require './base_controller' +FeedbackController = require './feedback/feedback_controller' +FooterController = require './footer/footer_controller' +GitHubUser = require '../models/site/github_user' +HeaderController = require './header/header_controller' +ImageLoader = require './image_loader' +Mod = require '../models/game/mod' +ModPack = require '../models/game/mod_pack' +Router = require './router' +Storage = require './storage' + +######################################################################################################################## + +module.exports = class SiteController extends BaseController + + constructor: (options={})-> + options.el = 'html' + super options + + @client = options.client + @imageLoader = new ImageLoader defaultUrl:'/images/unknown.png' + @modPack = new ModPack + @router = new Router this + @storage = new Storage storage:global.localStorage + + @_currentPage = null + @_currentPageController = null + @_user = null + + # Public Methods ############################################################################### + + loadDefaultModPack: -> + makeResponder = (m)-> return -> + m.activeModVersion.fetch() if m.activeModVersion? + + for modSlug, modData of c.defaultMods + mod = new Mod slug:modSlug + mod.on c.event.change + ':activeModVersion', makeResponder mod + @storage.register "mod:#{mod.slug}", mod, 'activeVersion', modData.defaultVersion + mod.fetch() + + @modPack.addMod mod + + if global.env isnt 'prerender' + @modPack.once c.event.sync, => + @$pageContent.css 'display', '' + @$pageContentLoading.css 'display', 'none' + + loadCurrentUser: -> + @client.fetchCurrentUser() + .then (response)=> + userData = response.json?.data?.user + @user = new GitHubUser userData if userData? + .catch (error)=> + if error?.response?.statusCode isnt 401 + logger.error "Failed to get current user: #{error}" + else + logger.info "User is not logged in" + .done() + + login: -> + @storage.store 'post-login-url', window.location.pathname + @router.navigate c.url.login(), trigger:true + + logout: -> + @client.logout() + .then => + @storage.store 'loginSecurityToken', null + @user = null + .catch (error)-> + logger.error -> "Failed to log out: #{error}" + .done() + + resumeAfterLogin: -> + url = @storage.load 'post-login-url' + url = if (not url? or url is 'null') then null else url + if url? then @router.navigate url, trigger:true + @storage.store 'post-login-url', null + + # Property Methods ############################################################################# + + getControllerOptions: -> + client: @client + imageLoader: @imageLoader + modPack: @modPack + router: @router + storage: @storage + enterFeedback: (message)=> @_feedbackController.enterFeedback(message) + user: @user + + getUser: -> + return @_user + + setUser: (newUser)-> + oldUser = @_user + return if newUser is oldUser + + @_user = newUser + logger.info -> "User changed to: #{newUser?.name}" + + @trigger c.event.change + ':user', this, oldUser, newUser + @trigger c.event.change, this + + if @_currentPageController? then @_currentPageController.user = newUser + + Object.defineProperties @prototype, + controllerOptions: { get:@::getControllerOptions } + user: { get:@::getUser, set:@::setUser } + + # BaseController Overrides ##################################################################### + + render: -> + @_footerController = @addChild FooterController, '.view__footer', @controllerOptions + @_headerController = @addChild HeaderController, '.view__header', @controllerOptions + + @$pageContent = @$('.page > .content') + @$pageContentLoading = @$('.page > .content-loading') + + @_feedbackController = @addChild FeedbackController, '.view__feedback' + + # Private Methods ############################################################################## + + setPage: (page, controller)-> + return if @_currentPageController is controller + + logger.info -> "changing to page controller: #{controller.constructor.name}" + + if @_currentPageController + @_currentPageController.unrender() + @_resetGlobals() + + @_currentPage = page + @_currentPageController = controller + + $pageContent = $('.page > .content') + $pageContent.removeClass() + $pageContent.addClass 'content' + + window.scrollTo 0, 0 + + @_headerController.model = controller: controller + + @_currentPageController.user = @user + @_currentPageController.onWillShow() + @_currentPageController.$el = $pageContent + @_currentPageController.render() + + _resetGlobals: -> + if global.env in c.productionEnvs + for key, value of global + if key.indexOf('google') isnt -1 + delete global[key] + + delete global.adsByGoogle + $('script[src="//pagead2.googlesyndication.com/pagead/js/adsbygoogle.js"]').remove() + $('body').append('') diff --git a/src/coffee/models/storage.coffee b/src/client/site/storage.coffee similarity index 94% rename from src/coffee/models/storage.coffee rename to src/client/site/storage.coffee index 0c4804ecd..092a123bb 100644 --- a/src/coffee/models/storage.coffee +++ b/src/client/site/storage.coffee @@ -1,9 +1,9 @@ -### -Crafting Guide - storage.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### +# +# Crafting Guide - storage.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# ######################################################################################################################## diff --git a/src/client/site/templates.js b/src/client/site/templates.js new file mode 100644 index 000000000..af05bcef6 --- /dev/null +++ b/src/client/site/templates.js @@ -0,0 +1,260 @@ +var jade = jade || require('jade/lib/runtime'); + +this["JST"] = this["JST"] || {}; + +this["JST"]["browse_page"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
");;return buf.join(""); +}; + +this["JST"]["browse_page/mod_tile"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

");;return buf.join(""); +}; + +this["JST"]["common/adsense"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
");;return buf.join(""); +}; + +this["JST"]["common/crafting_grid"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
");;return buf.join(""); +}; + +this["JST"]["common/inventory"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
nothing

add an item...

clear

");;return buf.join(""); +}; + +this["JST"]["common/item_group"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

");;return buf.join(""); +}; + +this["JST"]["common/item_group/item_tile"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

");;return buf.join(""); +}; + +this["JST"]["common/item_selector/element"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
");;return buf.join(""); +}; + +this["JST"]["common/item_selector"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
");;return buf.join(""); +}; + +this["JST"]["common/markdown_section/markdown_image_list/markdown_image"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

checking for image...

");;return buf.join(""); +}; + +this["JST"]["common/markdown_section/markdown_image_list"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

Images Referenced

");;return buf.join(""); +}; + +this["JST"]["common/markdown_section"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

Please help by adding a description!

Edit using GitHub\nFlavored Markdown. Use [[Item Name]] to link to another item and ![](image.png)\nto add an image.

edit

save

preview

cancel

return

Thanks for your help!

Your changes will appear on the site in a few minutes.

Sorry, but something went wrong.

Please try again after a few moments.

");;return buf.join(""); +}; + +this["JST"]["common/recipe"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
");;return buf.join(""); +}; + +this["JST"]["common/slot"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
");;return buf.join(""); +}; + +this["JST"]["common/stack"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

 

 

");;return buf.join(""); +}; + +this["JST"]["common/video"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

");;return buf.join(""); +}; + +this["JST"]["craft_page"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push(""); +var quarryHref = '/craft/quarry' +var quarry +var quantumSuitHref = '/craft/quantumsuit_bodyarmor:quantumsuit_boots:quantumsuit_helmet:quantumsuit_leggings' +var ic2Href = '/browse/industrial_craft_2' +var solarPanelHref = '/craft/solar_panel_vi' +var solarFluxHref = '/browse/solar_flux' +buf.push("

Instructions

Crafting Guide provides step-by-step instructions for thousands of items from Minecraft and many\npopular mods. Just click \"Add an item...\" down below.

Not sure what you'd like to make? Try one of these:

Items to Make

Already in Inventory

Need to Gather

Steps

");;return buf.join(""); +}; + +this["JST"]["craft_page/craftsman_working"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

");;return buf.join(""); +}; + +this["JST"]["craft_page/step"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

complete step

make this tool

");;return buf.join(""); +}; + +this["JST"]["feedback"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

Sending failed. Please try again later.

send

Feedback

");;return buf.join(""); +}; + +this["JST"]["footer"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

About

Crafting Guide gives step-by-step instructions for making anything in Minecraft or its many mods. Just\nsay what you'd like to make, what you already have, it will do the rest, giving you a list of raw\nmaterials and instructions of which items to make in the proper order. You can even ask it to include\nthe materials and instructions for all the tools you'll need along the way!\n

Donate

Crafting Guide is free for all, but if you find it helpful, donations in any amount are gratefully\naccepted.

Get Involved

Crafting Guide is completely open-source, and you can help! Whether you want to write a recipe book\n(all simple JSON), or implement new features, just head over to GitHub to get started.

");;return buf.join(""); +}; + +this["JST"]["header"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

Minecraft Crafting Guide

Craft

Browse

News

Search

Login

");;return buf.join(""); +}; + +this["JST"]["item_page"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

View Crafting Plan

Official Link:project page

Multiblock Construction

Recipes

Videos

");;return buf.join(""); +}; + +this["JST"]["item_page/multiblock_viewer/multiblock"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
");;return buf.join(""); +}; + +this["JST"]["item_page/multiblock_viewer"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

Complete Materials

Current Layer

back

next

 

");;return buf.join(""); +}; + +this["JST"]["item_page/recipe_detail"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

Ingredients

Produces

");;return buf.join(""); +}; + +this["JST"]["login_page"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

Login with GitHub

Use your GitHub credentials to login and make changes on Crafting Guide. No GitHub account? Don't\nworry, you can get one for free. read more...\n

All changes you make on the site get submitted directly to our GitHub repo, and then published\nthrough the same automated deployment process as changes made by anyone else. That way, anyone\ncan contribute easily: whether developer or end user.

To log in, we redirect you to GitHub's site, and once you're signed in, they'll send you back\nhere. We never see your credentials, and only get the minimum set of permissions necessary to\nsubmit changes to the Crafting Guide repo on your behalf.

GitHub offers free accounts, so even if you don't already have one, you've got nothing to lose!\n

Login with GitHub

Completing log in...

Hang on just a second while we finish logging you in...

Oops!

Sorry about that, but it looks like something went wrong with your GitHub login. Click the button below\nto try again, or use the Feedback button on the left to let us know, and we'll try to help.\n

Login with GitHub

All set!

You are logged in to CraftingGuide using the following GitHub account:

You will be redirected shortly.

Logout

Sorry!

Our interactive editing service is down right now, but you can always submit a pull request over at the\nCrafting Guide GitHub Repository. We'll\nhave the editing service back up soon!

");;return buf.join(""); +}; + +this["JST"]["mod_page"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
in my mod pack
PLEASE NOTE: By selecting \"no\", crafting plans, search, and other features will ignore items\nand recipes from this mod.

Tutorials

");;return buf.join(""); +}; + +this["JST"]["mod_page/tutorial"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

");;return buf.join(""); +}; + +this["JST"]["news_page"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("

2015-02-11

I've been using Modular PowerSuits myself lately, and I\nnoticed that the newest version (finally!) comes with default recipes. So, I've updated\nCrafting Guide to support both the newest vanilla recipes as well as those from Thermal\nExpansion. You can switch back and forth on the Configure page.\n

2015-02-09

Back before the winter holidays, the extremely patient \ntdallmann completed support for Hydraulicraft, and I'm\nafraid I'm only now getting it up on the site! It looks like a neat mod based all around the\nscience of hydraulics with a nicely stepped set of devices to be made at each level. Many thanks\nto tddallmann for adding it to Crafting Guide!

I also received a submission for adding OpenComputers from\nyut23. Should be a big help to those aspiring Minecraft\nprogrammers who want a bit more challege than is provided by \nComputerCraft! Thanks, yut23!\n

2015-11-25

With many thanks to Mike Caron, I'm pleased to announce\nsupport for Storage Drawers!\n

2015-12-13

I'm super excited to announce that I've added full multi-block support for Crafting Guide! For\nexample, check out a 5-Core Reactor\nfrom Big Reactors, or the 5x5x5 Steel Tank from\nRailcraft. I'm really pleased with how it turned out!\n

2015-11-17

And today, it's Extra Cells!\n

2015-11-16

It's a small one, but also highly requested... Here's ComputerCraft!\n

2015-11-14

One more small one over the weekend... Advanced Solar\nPanels has been added to crafting guide!\n

2015-11-14

For a long while now, Galacticraft has been the most\nrequested mod, and it's finally here! Enjoy!\n

2015-11-10

Remember me? They guy who runs the site. Yeah, I'm back, and with big news! The site now has\na completely new crafting algorithm. Instead of just taking the first crafting plan it comes up\nwith, it tries to compute every possible plan, rates them, and then picks the best one. This\nalso clears up a lot of bugs related to the old algorithm. The one drawback is that some items\ncan take a bit longer to compute than with the old way, but I think you'll find it's worth it!

On a personal note, I think it's clear that I don't have nearly as much time to dedicate to the\nsite as I used to. That's mostly because I started a new job which keeps me away from working\non the site so much. I hope to be able to get into a more regular pace now things my personal\nlife has settled down again.\n

2015-07-25

You may have noticed things have been very quiet with the site for the past month... well I'm\nafraid that's because I haven't been working on it. Instead, I've been hunting for a new job.\nNow that I've got that all squared away (I'll be starting at Looker in Santa Cruz on Monday),\nI'll have nights and weekends to continue working on the site. Thanks for being patient!\n

2015-06-12

Today I launched the second major part of the item description editor: image uploads! As you\nenter your description, use the markdown notation for an image ![](image.png) and a\nempty image preview will show up underneath the editor. Click the button to select an image from\nyour computer. Just be sure to keep the images to a reasonable size (< 750kB, and < 740px by\n600px).\n

2015-05-13

As of today, you can now add and edit item descriptions right on Crafting Guide. This feature is\nstarting small with just item descriptions, but eventually all the content on the site will be\neditable. All you need is a (free) GitHub account, and you're ready to go!

For those more comfortable with a regular text editor, all the content is still in GitHub under\nthe crafting-guide-data repo.\nJust follow the instructions, and you can submit content via pull request instead of using the\nwebsite's editor.\n

2015-04-30

I've been working on a big new feature for a while now, but I didn't want to leave everyone\nwithout anything new for so long... So, I've just finished adding MineFactory Reloaded! Enjoy!\n

2015-04-20

Okay... big changes on the crafting page! Instead of having four little boxes for the various\nparts of the crafting plan, the new page shows all the steps as one long list. In addition, you\nget a lot more control over the plan. Now, you can even mark individual steps as complete to get\na new crafting plan which doesn't include those items.

As an example, let's say you're thinking about upgrading your Reinforced Jetpack to a shiny new Resonant Jetpack, you can just mark off the\nstep for the Reinforced Jetpack, and get only the materials and steps for doing the upgrade.\nI'm really pleased with the new crafting page, and I think you're going to love it!\n

2015-04-11

I've just finished adding Simply Jetpacks by Tonius. It\nseems like a simple mod on the surface, but what with all the upgrades and technology tiers, it\ntakes an amazing 87 steps to make the highest-tier\njetpack!

I've also added Solar Flux by Nauktis. Again, another\ndeceptively simple mod, but the most powerful solar\npanel kicks out an impressive 4096 RF/t! I just hope your mine has been productive... among\nother things, you'll need 45 Diamonds, 110 Gold Ore, 1568 Copper Ore, and 6023 Iron Ore!

");;return buf.join(""); +}; + +this["JST"]["tutorial_page"] = function template(locals) { +var buf = []; +var jade_mixins = {}; +var jade_interp; + +buf.push("
a tutorial for
from

");;return buf.join(""); +}; + +if (typeof exports === 'object' && exports) {module.exports = this["JST"];} \ No newline at end of file diff --git a/src/client/site/tutorial_page/tutorial_page.jade b/src/client/site/tutorial_page/tutorial_page.jade new file mode 100644 index 000000000..4d7ff9453 --- /dev/null +++ b/src/client/site/tutorial_page/tutorial_page.jade @@ -0,0 +1,26 @@ +//- +//- Crafting Guide - tutorial_page.jade +//- +//- Copyright © 2014-2016 by Redwood Labs +//- All rights reserved. +//- + +.view__tutorial_page + .left + .view__adsense + + .right + .about + .left + img + .right + .title + .sourceMod a tutorial for + .officialLink from + + .tutorial-sections + + section.videos + h2 + .panel + .video-container diff --git a/src/client/site/tutorial_page/tutorial_page.scss b/src/client/site/tutorial_page/tutorial_page.scss new file mode 100644 index 000000000..909b29742 --- /dev/null +++ b/src/client/site/tutorial_page/tutorial_page.scss @@ -0,0 +1,62 @@ +// +// Crafting Guide - tutorial_page.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.view__tutorial_page { + @include layout-body-with-sidebar; + + .about { + display: flex; + margin-bottom: $size-margin-large; + + & > .left { + margin-right: $size-margin-large; + + flex: 0 0 auto; + + img { + height: $size-minecraft-block * 5; + width: $size-minecraft-block * 5; + } + } + + & > .right { + flex: 1 1 100%; + + .title { + font-family: $font-family-header; + font-size: $font-size-xxlarge; + } + + .sourceMod { + font-family: $font-family-text; + font-size: $font-size-medium; + } + + .officialLink { + font-family: $font-family-text; + font-size: $font-size-medium; + } + } + } + + .tutorial-sections { + } + + .video-container { + margin-right : -$size-margin-medium; + margin-top : -$size-margin-medium; + display : flex; + flex-wrap : wrap; + + & > * { + flex : 1 1 100%; + margin-right : $size-margin-medium; + margin-top : $size-margin-medium; + max-width : calc(50% - 12px); // $size-margin-medium + } + } +} diff --git a/src/client/site/tutorial_page/tutorial_page_controller.coffee b/src/client/site/tutorial_page/tutorial_page_controller.coffee new file mode 100644 index 000000000..0f37b4452 --- /dev/null +++ b/src/client/site/tutorial_page/tutorial_page_controller.coffee @@ -0,0 +1,171 @@ +# +# Crafting Guide - tutorial_page_controller.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +AdsenseController = require '../common/adsense/adsense_controller' +PageController = require '../page_controller' +MarkdownSectionController = require '../common/markdown_section/markdown_section_controller' +VideoController = require '../common/video/video_controller' + +######################################################################################################################## + +module.exports = class TutorialPageController extends PageController + + constructor: (options={})-> + if not options.client? then throw new Error 'options.client is required' + if not options.modSlug? then throw new Error 'options.modSlug is required' + if not options.tutorialSlug? then throw new Error 'options.tutorialSlug is required' + if not options.modPack? then throw new Error 'options.modPack is required' + + options.model ?= null + options.templateName = 'tutorial_page' + super options + + @_client = options.client + @_modPack = options.modPack + @_modSlug = options.modSlug + @_tutorialSlug = options.tutorialSlug + + @_modPack.on c.event.change, => @_resolveTutorial() + @_resolveTutorial() + + # PageController Overrides ##################################################################### + + getTitle: -> + return null unless @model? + return @model.name + + getBreadcrumbs: -> + return [] unless @model? and @_modSlug? + + mod = @_modPack.getMod(@_modSlug) + + return [ + $("Browse") + $("#{mod.name}") + $("#{@model.name}") + ] + + # BaseController Overrides ##################################################################### + + onDidRender: -> + @_adsenseController = @addChild AdsenseController, '.view__adsense', model:'skyscraper' + + @$sourceModLink = @$('.sourceMod a') + @$officialLink = @$('.officialLink a') + @$officialLinkPanel = @$('.officialLink') + @$title = @$('.title') + @$titleImage = @$('.about img') + @$tutorialSections = @$('.tutorial-sections') + @$videosSection = @$('.videos') + @$videosSectionPanel = @$('.video-container') + @$videosSectionTitle = @$('.videos h2') + super + + refresh: -> + if @model? and @model.isLoaded + @_refreshOfficialLink() + @_refreshSourceModLink() + @_refreshTutorialSections() + @_refreshTutorialTitle() + @_refreshVideos() + + @show() + else + @hide() + + super + + # Private Methods ############################################################################## + + _refreshSourceModLink: -> + @$sourceModLink.html @_modPack.getMod(@_modSlug).name + @$sourceModLink.attr 'href', c.url.mod modSlug:@_modSlug + + _refreshOfficialLink: -> + if @model.officialUrl? + @$officialLink.attr 'href', @model.officialUrl + @show @$officialLinkPanel + else + @hide @$officialLinkPanel + + _refreshTutorialTitle: -> + @$title.html @model.name + @$titleImage.attr 'src', c.url.tutorialIcon modSlug:@_modSlug, tutorialSlug:@_tutorialSlug + + _refreshTutorialSections: -> + @_sectionControllers ?= [] + index = 0 + + for section in @model.sections + controller = @_sectionControllers[index] + if not controller? + controller = new MarkdownSectionController + tagName: 'section' + client: @_client + title: section.title + model: section.content + modPack: @_modPack + @_sectionControllers.push controller + @$tutorialSections.append controller.$el + controller.render() + else + controller.title = section.title + controller.model = section.model + controller.refresh() + + controller.imageBase = c.url.tutorialImageDir modSlug:@_modSlug, tutorialSlug:@_tutorialSlug + index += 1 + + while @_sectionControllers.length > index + @_sectionController.pop().remove() + + _refreshVideos: -> + @_videoControllers ?= [] + index = 0 + + videos = @model?.videos or [] + if videos? and videos.length > 0 + @$videosSectionTitle.html if videos.length is 1 then 'Video' else 'Videos' + + for video in videos + controller = @_videoControllers[index] + if not controller? + controller = new VideoController model:video + @_videoControllers.push controller + @$videosSectionPanel.append controller.$el + controller.render() + else + controller.model = video + + index += 1 + + @show @$videosSection + else + @hide @$videosSection + + while @_videoControllers.length > index + @_videoControllers.pop().remove() + + _resolveTutorial: -> + return if @model? + + mod = @_modPack.getMod @_modSlug + if not mod? + logger.error => "cannot find the mod for: #{@_modSlug}" + router.navigate '/', trigger:true + return + + if not mod.isLoaded + mod.fetch() + return + + @model = mod.getTutorial @_tutorialSlug + if not @model? + logger.error => "mod #{@_modSlug} doesn't have a tutorial for: #{@_tutorialSlug}" + return + + @model.fetch() diff --git a/src/coffee/url_params.coffee b/src/client/site/url_params.coffee similarity index 91% rename from src/coffee/url_params.coffee rename to src/client/site/url_params.coffee index 0df55e41b..68f5c4e73 100644 --- a/src/coffee/url_params.coffee +++ b/src/client/site/url_params.coffee @@ -1,11 +1,10 @@ -### -Crafting Guide - url_params.coffee +# +# Crafting Guide - storage.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' url = require 'url' ######################################################################################################################## diff --git a/src/client/styles/classes.scss b/src/client/styles/classes.scss new file mode 100644 index 000000000..0bef669c9 --- /dev/null +++ b/src/client/styles/classes.scss @@ -0,0 +1,88 @@ +// +// Crafting Guide - classes.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.blur { + @include blur(2px); +} + +.button { + min-height : $size-button-height; + position : relative; + + background : $color-button-background url('/images/button-background-normal.png') repeat; + cursor : pointer; + @include no-select; + + .bezel { + position: absolute; top: 0; right: 0; bottom: 0; left: 0; + + border-top : 3px solid $color-button-highlight; + border-left : 3px solid $color-button-highlight; + border-bottom : 6px solid $color-button-shadow; + border-right : 3px solid $color-button-shadow; + + p { + position : absolute; + min-height : 100%; + top : 50%; + width : 100%; + transform : translateY(-8px); + + color : $color-white; + font-family : $font-family-header; + font-size : 20px; + overflow-x : hidden; + text-align : center; + text-overflow : ellipsis; + user-select : none; + white-space : nowrap; + } + } + + &:hover { + background : url('/images/button-background-hover.png') repeat; + } + + &:active { + background : url('/images/button-background-active.png') repeat; + + .bezel { + border: 0; + } + } + + &.disabled { + background : $color-gray-faint; + cursor : default; + + .bezel { + border: 2px solid $color-gray-light; + + p { + color: $color-gray-light; + } + } + } +} + +.page > .content { + min-height: $size-skyscraper-height; +} + +.skyscraper { + height : $size-skyscraper-height - 2px; + width : $size-skyscraper-width - 2px; + + border : 1px solid $color-gray-medium; +} + +.scrollDisabled { + position : fixed; + margin-top : 0; + width : 100%; + overflow-y : scroll; +} diff --git a/src/client/styles/colors.scss b/src/client/styles/colors.scss new file mode 100644 index 000000000..8293d21fb --- /dev/null +++ b/src/client/styles/colors.scss @@ -0,0 +1,51 @@ +// +// Crafting Guide - colors.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +// Raw Colors ////////////////////////////////////////////////////////////////////////////////////////////////////////// + +$color-bedrock : #0A0A0A; +$color-black : #000000; +$color-blue-dark : #484880; +$color-blue-faint : #EFEDFF; +$color-blue-light : #6256EF; +$color-blue-medium : #5E5ABF; +$color-brown-dark : #3D1D09; +$color-dirt : #906647; +$color-gray-dark : #474747; +$color-gray-faint : #EFEFEF; +$color-gray-light : #D0D0D0; +$color-gray-medium : #6C6C6C; +$color-ice : #AAC9FF; +$color-planks : #B7955E; +$color-shadow : #666666; +$color-white : #FFFFFF; + +// Semantic Colors ///////////////////////////////////////////////////////////////////////////////////////////////////// + +$color-active : #5C8AE6; +$color-active-hover : #2E6BE6; + +$color-background-footer : $color-brown-dark; +$color-background-page : rgba(230, 230, 230, 0.75); +$color-background-panel : rgba(255, 255, 255, 0.90); +$color-background-window : $color-ice; + +$color-button-background : #6F6F6F; +$color-button-highlight : rgba(255, 255, 255, 0.66); +$color-button-shadow : rgba(0, 0, 0, 0.33); + +$color-error : #DD444A; + +$color-link-normal : $color-blue-medium; +$color-link-active : $color-blue-light; +$color-link-visited : $color-blue-dark; + +$color-screen : rgba(255, 255, 255, 0.50); + +$color-text : $color-black; +$color-text-secondary : $color-gray-medium; +$color-text-light : $color-white; diff --git a/src/client/styles/fonts.scss b/src/client/styles/fonts.scss new file mode 100644 index 000000000..141400218 --- /dev/null +++ b/src/client/styles/fonts.scss @@ -0,0 +1,36 @@ +// +// Crafting Guide - fonts.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +// Raw Fonts /////////////////////////////////////////////////////////////////////////////////////////////////////////// + +@font-face { + font-family : 'silkscreen'; + font-style : normal; + font-weight : 400; + src : url('/fonts/silkscreen.ttf') format('truetype'); +} + +@font-face { + font-family : 'aller'; + font-style : normal; + font-weight : 400; + src : url('/fonts/aller-regular.ttf') format('truetype'); +} + +// Semantic Fonts ////////////////////////////////////////////////////////////////////////////////////////////////////// + +$font-family-control : 'aller', sans-serif; +$font-family-header : 'silkscreen', monospace; +$font-family-input : monospace; +$font-family-text : 'aller', sans-serif; + +$font-size-xsmall : 10px; +$font-size-small : 12px; +$font-size-medium : 16px; +$font-size-large : 18px; +$font-size-xlarge : 24px; +$font-size-xxlarge : 36px; diff --git a/src/client/styles/layers.scss b/src/client/styles/layers.scss new file mode 100644 index 000000000..c7c9d1e34 --- /dev/null +++ b/src/client/styles/layers.scss @@ -0,0 +1,10 @@ +// +// Crafting Guide - layers.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +$layer-normal: 100; +$layer-screen: 1000; +$layer-dialog: 10000; diff --git a/src/client/styles/main.scss b/src/client/styles/main.scss new file mode 100644 index 000000000..bbf907fc9 --- /dev/null +++ b/src/client/styles/main.scss @@ -0,0 +1,23 @@ +// +// Crafting Guide - main.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +// normalize all values +@import './reset'; + +// define variables +@import './colors'; +@import './fonts'; +@import './layers'; +@import './mixins'; +@import './sizes'; + +// define globals styles +@import './classes'; +@import './tags'; + +// define special styles for markdown translation +@import './markdown'; diff --git a/src/client/styles/markdown.scss b/src/client/styles/markdown.scss new file mode 100644 index 000000000..96d405be9 --- /dev/null +++ b/src/client/styles/markdown.scss @@ -0,0 +1,97 @@ +// +// Crafting Guide - markdown.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +.markdown { + + a { + color: $color-link-normal; + text-decoration: none; + + &:hover { + color: $color-link-active; + text-decoration: underline; + } + } + + h1 { + font-family: $font-family-text; + font-size: $font-size-large; + font-weight: bold; + margin: $size-margin-large 0 $size-margin-small 0; + } + + img { + max-width: 100%; + } + + p { + font-family: $font-family-text; + font-size: $font-size-medium; + line-height: $font-size-medium * 1.25; + margin-top: $size-margin-medium; + } + + table { + margin: 2em auto 0 auto; + + td { + font-family: $font-family-text; + font-size: $font-size-medium; + padding: $size-margin-xxsmall $size-margin-medium; + vertical-align: middle; + } + + th { + font-family: $font-family-text; + font-size: $font-size-medium; + font-weight: bold; + padding: $size-margin-xxsmall $size-margin-medium; + vertical-align: middle; + text-align: center; + } + + td[align="center"] { + text-align: center; + } + td[align="right"] { + text-align: right; + } + } + + ol { + margin: $size-margin-large; + margin-bottom: 0; + + li { + font-family: $font-family-text; + font-size: $font-size-medium; + line-height: $font-size-medium * 1.25; + list-style: decimal; + margin: $size-margin-medium 0 0 $size-margin-large; + } + } + + + ul { + margin: $size-margin-large; + margin-bottom: 0; + + li { + font-family: $font-family-text; + font-size: $font-size-medium; + line-height: $font-size-medium * 1.25; + list-style: disc; + margin: $size-margin-medium 0 0 $size-margin-large; + } + } + + & > * { + &:first-child { + margin-top: 0; + } + } +} diff --git a/src/client/styles/mixins.scss b/src/client/styles/mixins.scss new file mode 100644 index 000000000..1e15a7a3b --- /dev/null +++ b/src/client/styles/mixins.scss @@ -0,0 +1,82 @@ +// +// Crafting Guide - mixins.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +@mixin blur($radius) { + -webkit-filter : blur($radius); + filter : blur($radius); +} + +@mixin grayscale { + -webkit-filter : grayscale(100%); + -moz-filter : grayscale(100%); + -ms-filter : grayscale(100%); + -o-filter : grayscale(100%); + filter : gray; +} + +@mixin no-select { + -webkit-touch-callout : none; /* iOS Safari */ + -webkit-user-select : none; /* Chrome/Safari/Opera */ + -moz-user-select : none; /* Firefox */ + -ms-user-select : none; /* IE/Edge */ + user-select : none; /* non-prefixed version, currently not supported by any browser */ +} + +@mixin floating-panel { + background: $color-background-panel; + box-shadow: $size-margin-xxsmall $size-margin-xxsmall $size-margin-xsmall $color-shadow; +} + +@mixin layout-link-list { + display: flex; + flex-direction: column; + justify-content: center; + + p { + margin-bottom: $size-margin-small; + + font-family: $font-family-text; + font-size: $font-size-large; + } + + a { + margin-left: $size-margin-medium; + + font-family: $font-family-text; + font-size: $font-size-medium; + text-decoration: underline; + + &:not(:last-child) { + margin-bottom: $size-margin-medium; + } + } +} + +@mixin pixel-image { + image-rendering : -moz-crisp-edges; /* Firefox */ + image-rendering : -o-crisp-edges; /* Opera */ + image-rendering : -webkit-optimize-contrast; /* Webkit (non-standard naming) */ + image-rendering : crisp-edges; + -ms-interpolation-mode : nearest-neighbor; /* IE (non-standard property) */ +} + +@mixin layout-body-with-sidebar { + display: flex; + + & > .left { + flex: 0 0 $size-skyscraper-width + $size-margin-medium; + padding-right: $size-margin-medium; + } + + & > .right { + flex: 1 1 auto; + + section { + margin-bottom: $size-margin-large; + } + } +} diff --git a/src/client/styles/reset.scss b/src/client/styles/reset.scss new file mode 100644 index 000000000..3102465e3 --- /dev/null +++ b/src/client/styles/reset.scss @@ -0,0 +1,50 @@ +// +// http://meyerweb.com/eric/tools/css/reset/ +// v2.0 | 20110126 +// License: none (public domain) +// + +html, body, div, span, applet, object, iframe, +h1, h2, h3, h4, h5, h6, p, blockquote, pre, +a, abbr, acronym, address, big, cite, code, +del, dfn, em, img, ins, kbd, q, s, samp, +small, strike, strong, sub, sup, tt, var, +b, u, i, center, +dl, dt, dd, ol, ul, li, +fieldset, form, label, legend, +table, caption, tbody, tfoot, thead, tr, th, td, +article, aside, canvas, details, embed, +figure, figcaption, footer, header, hgroup, +menu, nav, output, ruby, section, summary, +textarea, time, mark, audio, video { + margin: 0; + padding: 0; + border: 0; + box-sizing: border-box; + font-size: 100%; + font: inherit; + vertical-align: baseline; +} +/* HTML5 display-role reset for older browsers */ +article, aside, details, figcaption, figure, +footer, header, hgroup, ins, menu, nav, section { + display: block; +} +body { + line-height: 1; +} +ol, ul { + list-style: none; +} +blockquote, q { + quotes: none; +} +blockquote:before, blockquote:after, +q:before, q:after { + content: ''; + content: none; +} +table { + border-collapse: collapse; + border-spacing: 0; +} \ No newline at end of file diff --git a/src/client/styles/sizes.scss b/src/client/styles/sizes.scss new file mode 100644 index 000000000..cc8a3d5c8 --- /dev/null +++ b/src/client/styles/sizes.scss @@ -0,0 +1,29 @@ +// +// Crafting Guide - sizes.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + + +$size-rem : 12px; // must be first + +$size-border-small : 1px; +$size-border-medium : 2px; +$size-border-large : 3px; + +$size-button-height : 40px; + +$size-margin-xxsmall : 2px; +$size-margin-xsmall : 4px; +$size-margin-small : 8px; +$size-margin-medium : 12px; +$size-margin-large : 24px; +$size-margin-xlarge : 48px; + +$size-minecraft-block : 32px; + +$size-page-width : $size-rem * 80; + +$size-skyscraper-height : 600px; +$size-skyscraper-width : 160px; diff --git a/src/client/styles/tags.scss b/src/client/styles/tags.scss new file mode 100644 index 000000000..9db57335f --- /dev/null +++ b/src/client/styles/tags.scss @@ -0,0 +1,54 @@ +// +// Crafting Guide - tags.scss +// +// Copyright © 2014-2016 by Redwood Labs +// All rights reserved. +// + +a { + color: $color-link-normal; + text-decoration: none; + + &:active { + color: $color-link-active; + } + + &:hover { + text-decoration: underline; + } + + &:visited { + color: $color-link-visited; + } +} + +button { + outline: none; +} + +h1 { + font-family: $font-family-header; + font-size: $font-size-xxlarge; +} + +h2 { + font-family: $font-family-header; + font-size: $font-size-xlarge; +} + +h3 { + font-family: $font-family-header; + font-size: $font-size-large; +} + +section { + display: flex; + flex-direction: column; + + .panel { + min-height: $size-margin-xlarge * 2; + + @include floating-panel; + padding: $size-margin-medium; + } +} \ No newline at end of file diff --git a/src/coffee/constants.coffee b/src/coffee/constants.coffee deleted file mode 100644 index a7957dfa6..000000000 --- a/src/coffee/constants.coffee +++ /dev/null @@ -1,165 +0,0 @@ -### -Crafting Guide - constants.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' - -exports.Adsense = Adsense = {} -Adsense.clientId = 'ca-pub-6593013914878730' -Adsense.slotIds = ['7613920409', '9574673605', '3388539204'] - -exports.DefaultMods = - minecraft: { defaultVersion: '1.7.10' } # Minecraft must be first - - advanced_solar_panels: { defaultVersion: '3.5.1' } - agricraft: { defaultVersion: '1.4.6' } - applied_energistics_2: { defaultVersion: 'rv1-stable-1' } - big_reactors: { defaultVersion: '0.4.2A2' } - buildcraft: { defaultVersion: '6.4.6' } - computercraft: { defaultVersion: '1.74' } - enderio: { defaultVersion: '2.2.7.325' } - ender_storage: { defaultVersion: '1.4.5.29' } - extra_cells: { defaultVersion: '2.2.73b129' } - extra_utilities: { defaultVersion: '1.2.2' } - forge_multipart: { defaultVersion: '1.2.0.345' } - forestry: { defaultVersion: '3.4.0.7' } - hydraulicraft: { defaultVersion: '2.1.242' } - galacticraft: { defaultVersion: '3.0.12.404' } - ic2_classic: { defaultVersion: 'none' } - industrial_craft_2: { defaultVersion: '2.2.663' } - iron_chests: { defaultVersion: '6.0.62.742' } - jabba: { defaultVersion: '1.2.1a' } - logistics_pipes: { defaultVersion: '0.9.3.100' } - mekanism: { defaultVersion: '7.1.1.127' } - minefactory_reloaded: { defaultVersion: '2.8.0RC8-86' } - modular_powersuits: { defaultVersion: '0.11.0-300-thermal-expansion' } - opencomputers: { defaultVersion: '1.5.22' } - quantum_flux: { defaultVersion: '1.3.4' } - railcraft: { defaultVersion: '9.5.0' } - simply_jetpacks: { defaultVersion: '1.4.1' } - storage_drawers: { defaultVersion: '1.7.10-1.6.2' } - solar_flux: { defaultVersion: '0.5b' } - thermal_dynamics: { defaultVersion: '1.0.0RC7-98' } - thermal_expansion: { defaultVersion: '4.0.0B8-23' } - -exports.Duration = Duration = {} -Duration.snap = 100 -Duration.fast = 200 -Duration.normal = 400 -Duration.slow = 1200 - -exports.Event = Event = {} -Event.add = 'add' # collection, item... -Event.animate = {} -Event.animate.hide = {} -Event.animate.hide.start = 'animate:hide:start' # controller, selector -Event.animate.hide.finish = 'animate:hide:finish' # controller, selector -Event.animate.show = {} -Event.animate.show.start = 'animate:show:start' # controller, selector -Event.animate.show.finish = 'animate:show:finish' # controller, selector -Event.button = {} -Event.button.complete = 'button:complete' # controller -Event.button.first = 'button:first' # controller, buttonType -Event.button.second = 'button:second' # controller, buttonType -Event.change = 'change' # model -Event.click = 'click' # event -Event.load = {} -Event.load.started = 'load:started' # controller, url -Event.load.succeeded = 'load:succeeded' # controller, book -Event.load.failed = 'load:failed' # controller, error message -Event.load.finished = 'load:finished' # controller -Event.remove = 'remove' # collection, item... -Event.request = 'request' # model -Event.route = 'route' -Event.sort = 'sort' -Event.sync = 'sync' # model, response -Event.transitionEnd = (-> - return 'transitionend' unless document? - transitions = - 'WebkitTransition': 'webkitTransitionEnd' - 'MozTransition': 'transitionend' - 'MSTransition': 'msTransitionEnd' - 'OTransition': 'oTransitionEnd' - 'transition': 'transitionend' - - el = document.createElement 'fakeelement' - for styleName, eventName of transitions - return eventName if el.style[styleName]? - - throw new Error 'cannot determine transitionEnd event' -)() - -exports.Key = Key = {} -Key.Enter = 13 -Key.Return = 13 -Key.Escape = 27 -Key.UpArrow = 38 -Key.DownArrow = 40 - -exports.GitHub = GitHub = {} -GitHub.file = {} -GitHub.file.itemDescription = {} -GitHub.file.itemDescription.fileName = _.template "item.cg" -GitHub.file.itemDescription.path = _.template "/data/<%= modSlug %>/items/<%= itemSlug %>" - -exports.Limits = Limits = {} -Limits.maximumGraphSize = 5000 -Limits.maximumPlanCount = 5000 - -exports.Login = Login = {} -Login.authorizeUrl = _.template "https://github.com/login/oauth/authorize" + - "?client_id=<%= clientId %>&scope=public_repo&state=<%= state %>" -Login.clientIds = - 'local': 'a2a1c5f1bb2d7bd14ebb' - 'staging': '655a38cde23040283361' - 'production': 'ea419abd2ab96c708815' - -exports.ModelState = ModelState = {} -ModelState.unloaded = 'unloaded' -ModelState.loading = 'loading' -ModelState.loaded = 'loaded' -ModelState.failed = 'failed' - -exports.Opacity = Opacity = {} -Opacity.hidden = 1e-6 -Opacity.shown = 1 - -exports.ProductionEnvs = [ 'staging', 'production' ] - -exports.RequiredMods = [ 'minecraft' ] - -exports.Text = Text = {} -Text.browseDescription = _.template 'Browse through complete item listings for over a dozen top mods and use the interactive crafting planner for step-by-step instructions' -Text.configDescription = _.template 'Configure the interactive crafting planner for your exact modpack and get step-by-step instructions for any item in your world' -Text.craftDescription = _.template 'Build anything in your Minecraft mod pack with a full list of materials and step-by-step instructions using our interactive crafting planner' -Text.homeDescription = _.template 'Find everything you need to know about your Minecraft mod pack and use the interactive crafting planner for step-by-step instructions and full lists of materials' -Text.itemDescription = _.template 'Make <%= itemName %> and the rest of <%= modName %> easy and use the interactive crafting planner for step-by-step instructions' -Text.modDescription = _.template 'Make <%= modName %> easy with tutorials, videos, and a full item listing along with an interactive crafting planner for step-by-step instructions' -Text.title = _.template 'Minecraft Crafting Guide' -Text.titleWithText = _.template '<%= text %> | Minecraft Crafting Guide' - -exports.Url = Url = {} -Url.crafting = _.template "/craft/<%= inventoryText %>" -Url.item = _.template "/browse/<%= modSlug %>/<%= itemSlug %>/" -Url.itemData = _.template "/data/<%= modSlug %>/items/<%= itemSlug %>/item.cg" -Url.itemImageDir = _.template "/data/<%= modSlug %>/items/<%= itemSlug %>" -Url.itemIcon = _.template "/data/<%= modSlug %>/items/<%= itemSlug %>/icon.png" -Url.login = _.template "/login" -Url.mod = _.template "/browse/<%= modSlug %>/" -Url.modData = _.template "/data/<%= modSlug %>/mod.cg" -Url.modIcon = _.template "/data/<%= modSlug %>/icon.png" -Url.modVersionData = _.template "/data/<%= modSlug %>/versions/<%= modVersion %>/mod-version.cg" -Url.root = _.template "/" -Url.tutorial = _.template "/browse/<%= modSlug %>/tutorials/<%= tutorialSlug %>/" -Url.tutorialData = _.template "/data/<%= modSlug %>/tutorials/<%= tutorialSlug %>/tutorial.cg" -Url.tutorialIcon = _.template "/data/<%= modSlug %>/tutorials/<%= tutorialSlug %>/icon.png" -Url.tutorialIcon = _.template "/data/<%= modSlug %>/tutorials/<%= tutorialSlug %>/icon.png" -Url.tutorialImageDir = _.template "/data/<%= modSlug %>/tutorials/<%= tutorialSlug %>" - -exports.UrlParam = UrlParam = {} -UrlParam.quantity = 'count' -UrlParam.recipe = 'recipeName' -UrlParam.includingTools = 'tools' diff --git a/src/coffee/controllers/base_controller.coffee b/src/coffee/controllers/base_controller.coffee deleted file mode 100644 index 28cc90200..000000000 --- a/src/coffee/controllers/base_controller.coffee +++ /dev/null @@ -1,248 +0,0 @@ -### -Crafting Guide - base_controller.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' -_ = require 'underscore' -backbone = require 'backbone' -views = require '../views' -{Duration} = require '../constants' -{Event} = require '../constants' - -######################################################################################################################## - -module.exports = class BaseController extends backbone.View - - constructor: (options={})-> - @tryRefresh = _.debounce @_tryRefresh, 100 - - @_children = [] - @_model = null - @_parent = options.parent - @_rendered = false - @_useAnimations = options.useAnimations ?= true - - @_loadTemplate options.templateName - super options - - # Public Methods ############################################################################### - - addChild: (Controller, atSelector, options={})-> - options.el = @$(atSelector)[0] - options.parent = this - - child = new Controller options - child.render options - @_children.push child - return child - - hide: ($el)-> - $el ?= @$el - $el.data 'target-visibility', 'hidden' - _.delay (=> @_adjustTargetVisibility $el), Duration.snap - - refresh: -> - logger.verbose => "#{this} refreshing" - - remove: -> - if @_useAnimations - logger.verbose => "#{this} is hiding element before removing it" - @once Event.animate.hide.finish, => - logger.verbose => "#{this} is removing its element from the DOM" - @$el.remove() - @off() - @hide() - else - @$el.remove() - @off() - - routeLinkClick: (event)-> - event.preventDefault() - href = $(event.target).attr 'href' - href ?= $(event.currentTarget).attr 'href' - logger.info "Re-routing link to internal navigation: #{href}" - - if href? and href.match /^http/ - window.location.href = href - else - router.navigate href, trigger:true - - show: ($el)-> - $el ?= @$el - if $el.hasClass('hiding') or $el.hasClass('hidden') - $el.data 'target-visibility', 'visible' - _.delay (=> @_adjustTargetVisibility $el), Duration.snap - - unrender: -> - @undelegateEvents() - @$el.empty() - - # Event Methods ################################################################################ - - onDidModelChange: -> - @tryRefresh() - - onDidModelSync: -> - @tryRefresh() - - onWillRender: -> # do nothing - - onDidRender: -> - @tryRefresh() - - onWillShow: -> # do nothing - - onDidShow: -> # do nothing - - onWillChangeModel: (oldModel, newModel)-> - if oldModel?.on? - @stopListening oldModel - if newModel?.on? - @listenTo newModel, 'sync', (e)=> @onDidModelSync e - @listenTo newModel, 'change', (e)=> @onDidModelChange e - return newModel - - # Property Methods ############################################################################# - - Object.defineProperties @prototype, - model: - get: -> @_model - set: (newModel)-> - return if @model is newModel - - newModel = @onWillChangeModel @_model, newModel - @_model = newModel - @tryRefresh() - - rendered: - get: -> @_rendered - - user: - get: -> @_user - set: (newUser)-> - @_user = newUser - @tryRefresh() - - # Backbone.View Overrides ###################################################################### - - events: -> - return {} - - render: (options={})-> - options.force ?= false - options.show ?= true - return this unless not @_rendered or options.force - - if not @_template? - logger.error => "Default render called for #{@constructor.name} without a template" - return this - - data = (@model?.toHash? and @model.toHash()) or @model or {} - logger.verbose => "#{this} rendering with data: #{data}" - $renderedEl = $($(@_template(data))[0]) - - @onWillRender() - @unrender() - - @$el.append $renderedEl.children() - @$el.addClass $renderedEl.attr 'class' - @$el.data $renderedEl.data() - @delegateEvents() - - @_rendered = true - @onDidRender() - - return this - - # Object Overrides ############################################################################# - - toString: -> - return "#{@constructor.name}.#{@cid}" - - # Private Methods ############################################################################## - - _adjustTargetVisibility: ($el)-> - priorTarget = $el.data 'prior-target' - - target = $el.data 'target-visibility' - target ?= 'visible' - $el.data 'prior-target', target - - return if priorTarget is target and $el.data 'animating' - - current = 'visible' - current = 'hiding' if $el.hasClass 'hiding' - current = 'hidden' if $el.hasClass 'hidden' - - prior = $el.data 'prior-visibility' - $el.data 'prior-visibility', current - - if target is current and current isnt prior - $el.removeData 'prior-visibility' - $el.removeData 'prior-target' - if target is 'visible' - @trigger Event.animate.show.finish, this, $el - logger.verbose => "#{this} is finished showing #{$el.selector}" - else if target is 'hidden' - @trigger Event.animate.hide.finish, this, $el - logger.verbose => "#{this} is finished hiding #{$el.selector}" - - return if current is target - - if not $el.hasClass 'hideable' - $el.addClass 'hideable' - _.defer => @_adjustTargetVisibility $el - - if target is 'hidden' - if current is 'visible' - logger.verbose => "#{this} is hiding \"#{$el.selector}\"" - $el.addClass 'hiding' - @trigger Event.animate.hide.start, this, $el - - $el.data 'animating', true - @_onAnimationComplete $el, Duration.normal, => - $el.removeData 'animating' - @_adjustTargetVisibility $el - else if current is 'hiding' - $el.removeClass 'hiding' - $el.addClass 'hidden' - _.defer => @_adjustTargetVisibility $el - else if target is 'visible' - if current is 'hidden' - logger.verbose => "#{this} is showing \"#{$el.selector}\"" - $el.removeClass 'hidden' - $el.addClass 'hiding' - @trigger Event.animate.show.start, this, $el - _.defer => @_adjustTargetVisibility $el - else if current is 'hiding' - $el.removeClass 'hiding' - - $el.data 'animating', true - @_onAnimationComplete $el, Duration.normal, => - $el.removeData 'animating' - @_adjustTargetVisibility $el - - _loadTemplate: (templateName)-> - if templateName? - @_template = views[templateName] - - _tryRefresh: -> - return unless @_rendered - @refresh() - - _onAnimationComplete: ($el, maxDuration, callback)-> - $el ?= @$el - maxDuration ?= Duration.slow - callback ?= -> # do nothing - - $el.off Event.transitionEnd - $el.one Event.transitionEnd, callback - - # One would very much like this not to be necessary, but because of the way CSS transitions work, they are - # frequently not triggered. Rather than try to avoid the multitude of corner cases where this can happen, this - # simply sets a timer to ensure the event does eventually trigger. Since we're only listening for the first - # event, if the transition end event *did* happen, then this is a no-op. -- Andrew 2015-04-18 - setTimeout (-> $el.trigger Event.transitionEnd), maxDuration diff --git a/src/coffee/controllers/browse_page_controller.coffee b/src/coffee/controllers/browse_page_controller.coffee deleted file mode 100644 index 5f6a6e70d..000000000 --- a/src/coffee/controllers/browse_page_controller.coffee +++ /dev/null @@ -1,65 +0,0 @@ -### -Crafting Guide - browse_page_controller.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -AdsenseController = require './adsense_controller' -ModController = require './mod_controller' -PageController = require './page_controller' -{Duration} = require '../constants' -{Event} = require '../constants' -{Text} = require '../constants' - -######################################################################################################################## - -module.exports = class BrowsePageController extends PageController - - constructor: (options={})-> - if not options.modPack? then throw new Error 'options.modPack is required' - options.templateName = 'browse_page' - super options - - @modPack = options.modPack - @modPack.on Event.change, => @tryRefresh() - - # PageController Overrides ##################################################################### - - getMetaDescription: -> - return Text.browseDescription() - - getTitle: -> - return 'Browse' - - # BaseController Overrides ##################################################################### - - onDidRender: -> - @adsenseController = @addChild AdsenseController, '.view__adsense' - @$modContainer = @$('.mods') - super - - refresh: -> - @adsenseController.fillAdPositions() - - @_controllers ?= [] - controllerIndex = 0 - - @modPack.eachMod (mod)=> - return unless mod.enabled - - controller = @_controllers[controllerIndex] - if not controller? - controller = new ModController model:mod - @_controllers.push controller - controller.render() - @$modContainer.append controller.$el - else - controller.model = mod - - controllerIndex += 1 - - while @_controllers.length > controllerIndex - @_controllers.pop().remove() - - super diff --git a/src/coffee/controllers/configure_page_controller.coffee b/src/coffee/controllers/configure_page_controller.coffee deleted file mode 100644 index dfa7e43a4..000000000 --- a/src/coffee/controllers/configure_page_controller.coffee +++ /dev/null @@ -1,43 +0,0 @@ -### -Crafting Guide - configure_page_controller.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -AdsenseController = require './adsense_controller' -PageController = require './page_controller' -ModPackController = require './mod_pack_controller' -{Text} = require '../constants' - -######################################################################################################################## - -module.exports = class ConfigurePageController extends PageController - - constructor: (options={})-> - if not options.modPack? then throw new Error 'options.modPack is required' - if not options.storage? then throw new Error 'options.storage is required' - options.templateName = 'configure_page' - super options - - @modPack = options.modPack - @storage = options.storage - - # PageController Overrides ##################################################################### - - getMetaDescription: -> - return Text.configDescription() - - getTitle: -> - return "Configure" - - # BaseController Overrides ##################################################################### - - onDidRender: -> - @adsenseController = @addChild AdsenseController, '.view__adsense' - @modPackController = @addChild ModPackController, '.view__mod_pack', model:@modPack, storage:@storage - super - - refresh: -> - @adsenseController.fillAdPositions() - super diff --git a/src/coffee/controllers/crafting_grid_controller.coffee b/src/coffee/controllers/crafting_grid_controller.coffee deleted file mode 100644 index c7b1b58e3..000000000 --- a/src/coffee/controllers/crafting_grid_controller.coffee +++ /dev/null @@ -1,45 +0,0 @@ -### -Crafting Guide - crafting_grid_controller.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -ImageLoader = require './image_loader' -SlotController = require './slot_controller' -{Duration} = require '../constants' -{Event} = require '../constants' - -######################################################################################################################## - -module.exports = class CraftingGridController extends BaseController - - constructor: (options={})-> - if not options.imageLoader? then throw new Error 'options.imageLoader is required' - if not options.modPack? then throw new Error 'options.modPack is required' - # options.model should be a recipe - options.templateName = 'crafting_grid' - super options - - @imageLoader = options.imageLoader - @modPack = options.modPack - - @modPack.on Event.change, => @tryRefresh() - - # BaseController Methods ####################################################################### - - onDidRender: -> - @slotControllers = [] - for el in @$('.view__slot') - controller = new SlotController el:el, imageLoader:@imageLoader, modPack:@modPack - controller.render() - @slotControllers.push controller - super - - refresh: -> - for i in [0...@slotControllers.length] - controller = @slotControllers[i] - controller.model = @model?.getStackAtSlot(i) - - super diff --git a/src/coffee/controllers/header_controller.coffee b/src/coffee/controllers/header_controller.coffee deleted file mode 100644 index 78d74edfe..000000000 --- a/src/coffee/controllers/header_controller.coffee +++ /dev/null @@ -1,124 +0,0 @@ -### -Crafting Guide - header_controller.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' -BaseController = require './base_controller' -ItemSelectorController = require './item_selector_controller' -_ = require 'underscore' -{Duration} = require '../constants' -{Event} = require '../constants' -{ProductionEnvs} = require '../constants' -{Url} = require '../constants' - -######################################################################################################################## - -module.exports = class HeaderController extends BaseController - - constructor: (options={})-> - if not options.client? then throw new Error 'options.client is required' - if not options.modPack? then throw new Error 'options.modPack is required' - if not options.storage? then throw new Error 'options.storage is required' - super options - - @client = options.client - @modPack = options.modPack - @storage = options.storage - @_user = options.user - - # Event Methods ################################################################################ - - onLoginLinkClicked: (event)-> - event.preventDefault() - - if @user? - @client.logout() - .then => - @storage.store 'loginSecurityToken', null - router.user = null - .catch (error)-> - logger.error -> "Failed to log out: #{error}" - .done() - else - router.login() - - onLogoClicked: -> - router.navigate '/', trigger:true - return false - - onNavItemClicked: (event)-> - return true unless $(event.currentTarget).attr('href')? - - router.navigate $(event.currentTarget).attr('href'), trigger:true - return false - - # Property Methods ############################################################################# - - getUser: -> - return @_user - - setUser: (user)-> - @_user = user - @tryRefresh() - - Object.defineProperties @prototype, - user: {get:@prototype.getUser, set:@prototype.setUser} - - # BaseController Overrides ##################################################################### - - render: -> - # Overriding render because the header is already part of the stock page layout, and we - # don't need to replace it here. - @_rendered = true - - @$navLinks = ($(el) for el in @$('.navBar a')) - @$loginName = @$('.login .name') - @$loginLink = @$('.login a') - - zIndex = @$navLinks.length + 100 - for $navLink in @$navLinks - $navLink.css 'z-index', zIndex-- - - if global.env in ProductionEnvs - addThisUrl = 'http://s7.addthis.com/js/300/addthis_widget.js?pubid=ra-54f3c9717b2e530d' - $('body').append "" - - @_itemSelector = @addChild ItemSelectorController, '.view__item_selector.search', - modPack: @modPack - onChoseItem: (itemSlug)=> @_goToItem(itemSlug) - - refresh: -> - if @user? - @$loginName.html "Hello #{router.user.login}!" - @$loginLink.html "Logout" - else - @$loginName.html '' - @$loginLink.html 'Login' - - for $navLink in @$navLinks - linkPage = $navLink.data('page') - if @model is linkPage - $navLink.addClass 'selected' - else - $navLink.removeClass 'selected' - - if @model.indexOf(linkPage) isnt -1 - $navLink.find('.dot').css 'opacity': 1; - else - $navLink.find('.dot').css 'opacity': 0; - - # Backbone.View Overrides ###################################################################### - - events: -> - return _.extend super, - 'click a.logo': 'onLogoClicked' - 'click .navBar a': 'onNavItemClicked' - 'click .login a': 'onLoginLinkClicked' - - # Private Methods ############################################################################## - - _goToItem: (itemSlug)-> - router.navigate Url.item(itemSlug:itemSlug.item, modSlug:itemSlug.mod), trigger:true diff --git a/src/coffee/controllers/home_page_controller.coffee b/src/coffee/controllers/home_page_controller.coffee deleted file mode 100644 index a376ecb15..000000000 --- a/src/coffee/controllers/home_page_controller.coffee +++ /dev/null @@ -1,36 +0,0 @@ -### -Crafting Guide - home_page_controller.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -AdsenseController = require './adsense_controller' -PageController = require './page_controller' -_ = require 'underscore' -{Text} = require '../constants' - -######################################################################################################################## - -module.exports = class HomeController extends PageController - - constructor: (options={})-> - options.templateName = 'home_page' - super options - - # PageController Overrides ##################################################################### - - getMetaDescription: -> - return Text.homeDescription() - - # BaseController Overrides ##################################################################### - - onDidRender: -> - @adsenseController = @addChild AdsenseController, '.view__adsense' - super - - # Backbone.View Overrides ###################################################################### - - events: -> - return _.extend super, - 'click a': 'routeLinkClick' diff --git a/src/coffee/controllers/inventory_controller.coffee b/src/coffee/controllers/inventory_controller.coffee deleted file mode 100644 index 9bef36ff9..000000000 --- a/src/coffee/controllers/inventory_controller.coffee +++ /dev/null @@ -1,153 +0,0 @@ -### -Crafting Guide - inventory_controller.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -ImageLoader = require './image_loader' -ItemSelectorController = require './item_selector_controller' -NameFinder = require '../models/name_finder' -StackController = require './stack_controller' -_ = require 'underscore' -{Duration} = require '../constants' -{Event} = require '../constants' -{Key} = require '../constants' - -######################################################################################################################## - -### -Events: - clear(this) - change(this) - add(this, itemSlug) - button:first(this, itemSlug) - button:second(this, itemSlug) -### -module.exports = class InventoryController extends BaseController - - @MAX_QUANTITY = 9999 - - @ONLY_DIGITS = /^[0-9]*$/ - - constructor: (options={})-> - if not options.imageLoader? then throw new Error 'options.imageLoader is required' - if not options.modPack? then throw new Error 'options.modPack is required' - - @imageLoader = options.imageLoader - @modPack = options.modPack - - @editable = options.editable ?= true - @icon = options.icon ?= '/images/chest_front.png' - @firstButtonType = options.firstButtonType ?= null - @isAcceptable = options.isAcceptable ?= null - @secondButtonType = options.secondButtonType ?= null - @shouldEnableButton = options.shouldEnableButton ?= (model, button)-> true - @title = options.title ?= 'Inventory' - - options.templateName = 'inventory' - super options - - @_stackControllers = [] - - @listenTo @modPack, Event.change, => @refresh() - - # Event Methods ################################################################################ - - onClearButtonClicked: -> - return unless @model? - - @model.clear() - @trigger Event.clear, this - @trigger Event.change, this - - onFirstButtonClicked: (stackController)-> - @trigger Event.button.first, this, stackController?.model?.itemSlug - - onItemChosen: (itemSlug)-> - return unless @model? - - @model.add itemSlug, 1 - @trigger Event.add, this, itemSlug - @trigger Event.change, this - - onSecondButtonClicked: (stackController)-> - @trigger Event.button.second, this, stackController?.model?.itemSlug - - # BaseController Overrides ##################################################################### - - onDidRender: -> - @selector = @addChild ItemSelectorController, '.view__item_selector', - isAcceptable: @isAcceptable - modPack: @modPack, - onChoseItem: (itemSlug)=> @onItemChosen(itemSlug) - - @$clearButton = @$('.button.clear') - @$emptyPlaceholder = @$('.empty_placeholder') - @$icon = @$('.icon') - @$itemContainer = @$('.item_container') - @$title = @$('h2 p') - super - - refresh: -> - if @editable - @selector.show() - @show @$clearButton - else - @selector.hide() - @hide @$clearButton - - @$icon.attr 'src', @icon - @$title.html @title - - @_refreshStacks() - - @$clearButton.disabled = @model?.isEmpty - - if not @model or @model.isEmpty - @show @$emptyPlaceholder - else - @hide @$emptyPlaceholder - - super - - # Backbone.View Overrides ###################################################################### - - events: -> - return _.extend super, - 'click .button.clear': 'onClearButtonClicked' - 'click button.first': 'onFirstButtonClicked' - 'click button.second': 'onSecondButtonClicked' - - # Private Methods ############################################################################## - - _refreshStacks: -> - @_stackControllers ?= [] - index = 0 - - if @model? - @model.each (stack)=> - controller = @_stackControllers[index] - if not controller? - controller = new StackController - editable: @editable - firstButtonType: @firstButtonType - imageLoader: @imageLoader - model: stack - modPack: @modPack - secondButtonType: @secondButtonType - shouldEnableButton: @shouldEnableButton - controller.on Event.change, => @trigger Event.change, this - controller.on Event.button.first, (c)=> @onFirstButtonClicked(c) - controller.on Event.button.second, (c)=> @onSecondButtonClicked(c) - controller.render() - - @_stackControllers.push controller - @$itemContainer.append controller.$el - else - controller.model = stack - index += 1 - - while @_stackControllers.length > index - @_stackControllers.pop().remove() diff --git a/src/coffee/controllers/login_page_controller.coffee b/src/coffee/controllers/login_page_controller.coffee deleted file mode 100644 index 1d426b3ed..000000000 --- a/src/coffee/controllers/login_page_controller.coffee +++ /dev/null @@ -1,131 +0,0 @@ -### -Crafting Guide - login_page_controller.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -PageController = require './page_controller' -User = require '../models/user' -_ = require 'underscore' -{CraftingGuideClient} = require 'crafting-guide-common' -{Event} = require '../constants' -{Login} = require '../constants' -{Url} = require '../constants' - -######################################################################################################################## - -module.exports = class LoginPageController extends PageController - - @State: State = - ReadyToLogin: 'ready-to-login' - ServerDown: 'server-down' - InvalidCallback: 'invalid-callback' - FetchingToken: 'fetching-token' - LoggedIn: 'logged-in' - - constructor: (options={})-> - options.templateName = 'login_page' - - @client = options.client - @params = options.params - @storage = options.storage - - @_accessTokenLookupFailed = false - - @client.on Event.change + ':status', => @tryRefresh() - - super options - - # Event Methods ################################################################################ - - onExpandReadMore: (event)-> - event.preventDefault() - @$readMoreLink.addClass 'hidden' - @$readMoreContent.removeClass 'closed' - - onLoginButtonClicked: (event)-> - event.preventDefault() - @_redirectToGitHub() - - # Property Methods ############################################################################# - - getLoginSecurityToken: -> - @storage.load 'loginSecurityToken' - - setLoginSecurityToken: (value)-> - @storage.store 'loginSecurityToken', value - - Object.defineProperties @prototype, - loginSecurityToken: {get:@prototype.getLoginSecurityToken, set:@prototype.setLoginSecurityToken} - serverStatus: {get:@prototype.getServerStatus, set:@prototype.setServerStatus} - - # PageController Overrides ##################################################################### - - getTitle: -> - return "Login" - - # BaseController Methods ####################################################################### - - onDidRender: -> - @$readMoreLink = @$('a.read-more') - @$readMoreContent = @$('.read-more-content') - - if (not @user?) and (@params?.state?) and (@params?.state is @loginSecurityToken) - @client.completeGitHubLogin code:@params.code - .then (response)=> - attributes = response.json.data.user - if attributes? - router.user = new User attributes - router.resumeAfterLogin() - .catch (error)=> - logger.error "Failed to get access token: #{error}" - @_accessTokenLookupFailed = true - @refresh() - .done() - super - - refresh: -> - state = @_computeState() - @$('.two-thirds-content').addClass 'hidden' - @$(".two-thirds-content.#{state}").removeClass 'hidden' - - super - - # Backbone.View Overrides ###################################################################### - - events: -> - return _.extend super, - 'click a.read-more': 'onExpandReadMore' - 'click button': 'onLoginButtonClicked' - - # Private Methods ############################################################################## - - _computeState: -> - if @user? then return State.LoggedIn - - if @client.status is CraftingGuideClient.Status.Down then return State.ServerDown - - if @_accessTokenLookupFailed then return State.InvalidCallback - - if @params?.state? - if @params.state is @loginSecurityToken - return State.FetchingToken - else - return State.InvalidCallback - - return State.ReadyToLogin - - _compeleteLogin: (code)-> - @client.completeGitHubLogin code:code - .then (response)=> - router.user = new User response.json.user - .catch (error)=> - @_accessTokenLookupFailed = true - @refresh() - .done() - - _redirectToGitHub: -> - @loginSecurityToken = _.uuid() - clientId = Login.clientIds[global.env] - window.location.href = Login.authorizeUrl clientId:clientId, state:@loginSecurityToken diff --git a/src/coffee/controllers/mod_controller.coffee b/src/coffee/controllers/mod_controller.coffee deleted file mode 100644 index ee6f4f835..000000000 --- a/src/coffee/controllers/mod_controller.coffee +++ /dev/null @@ -1,40 +0,0 @@ -### -Crafting Guide - mod_controller.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -_ = require 'underscore' -{Url} = require '../constants' - -######################################################################################################################## - -module.exports = class ModController extends BaseController - - constructor: (options={})-> - if not options.model? then throw new Error 'options.model is required' - options.templateName = 'mod' - super options - - # BaseController Overrides ##################################################################### - - onDidRender: -> - @$link = @$('a') - @$logo = @$('.logo') - @$name = @$('.name p') - @$description = @$('.description p') - super - - refresh: -> - @$link.attr 'href', Url.mod modSlug:@model.slug - @$logo.attr 'src', Url.modIcon modSlug:@model.slug - @$name.html @model.name - @$description.html @model.description - - # Backbone.View Overrides ###################################################################### - - events: -> - return _.extend super, - 'click a': 'routeLinkClick' diff --git a/src/coffee/controllers/mod_pack_controller.coffee b/src/coffee/controllers/mod_pack_controller.coffee deleted file mode 100644 index 75673fc71..000000000 --- a/src/coffee/controllers/mod_pack_controller.coffee +++ /dev/null @@ -1,72 +0,0 @@ -### -Crafting Guide - mod_pack_controller.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -ModSelectorController = require './mod_selector_controller' -_ = require 'underscore' -{Duration} = require '../constants' - -######################################################################################################################## - -module.exports = class ModPackController extends BaseController - - constructor: (options={})-> - if not options.model? then throw new Error 'options.model is required' - options.templateName = 'mod_pack' - super options - - @storage = options.storage - - # Event Methods ################################################################################ - - onSuggestModClicked: -> - return unless global.feedbackController? - global.feedbackController.enterFeedback 'Please add mod:\n\n' - - # BaseController Overrides ##################################################################### - - onDidRender: -> - @$mods = @$('.mods') - @$toolbar = @$('.toolbar') - super - - refresh: -> - if global.feedbackController? - @$toolbar.show duration:0 - else - @$toolbar.hide duration:0 - - @_refreshMods() - super - - # Backbone.View Overrides ###################################################################### - - events: -> - return _.extend super, - 'click button[name="suggestMod"]': 'onSuggestModClicked' - - # Private Methods ############################################################################## - - _refreshMods: -> - @_modControllers ?= [] - index = 0 - - if @model? - @model.eachMod (mod)=> - controller = @_modControllers[index] - if not controller? - controller = new ModSelectorController model:mod, storage:@storage - controller.render() - @$mods.append controller.$el - @_modControllers.push controller - else - controller.model = mod - - index += 1 - - while @_modControllers.length > index - @_modControllers.pop().remove() diff --git a/src/coffee/controllers/mod_page_controller.coffee b/src/coffee/controllers/mod_page_controller.coffee deleted file mode 100644 index 4e9b7fd4a..000000000 --- a/src/coffee/controllers/mod_page_controller.coffee +++ /dev/null @@ -1,200 +0,0 @@ -### -Crafting Guide - mod_page_controller.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' -AdsenseController = require './adsense_controller' -Item = require '../models/item' -ItemGroupController = require './item_group_controller' -Mod = require '../models/mod' -ModPack = require '../models/mod_pack' -PageController = require './page_controller' -TutorialController = require './tutorial_controller' -{Duration} = require '../constants' -{Text} = require '../constants' -{Url} = require '../constants' - -######################################################################################################################## - -module.exports = class ModPageController extends PageController - - constructor: (options={})-> - if not options.imageLoader? then throw new Error 'options.imageLoader is required' - if not options.modPack? then throw new Error 'options.modPack is required' - options.delayStep ?= 10 - options.templateName = 'mod_page' - super options - - @imageLoader = options.imageLoader - @modPack = options.modPack - - @_delayStep = options.delayStep - @_effectiveModVersion = null - @_groupControllers = [] - - # Event Methods ################################################################################ - - onVersionChanged: -> - version = @$versionSelector.val() - modVersion = @model.getModVersion version - @_effectiveModVersion = modVersion - if modVersion? then modVersion.fetch() - @refresh() - - # Property Methods ############################################################################# - - getEffectiveModVersion: -> - return @_effectiveModVersion if @_effectiveModVersion? - return null unless @model? - - modVersion = @model.activeModVersion - modVersion ?= @model.getModVersion Mod.Version.Latest - modVersion.fetch() if modVersion? - - return modVersion - - Object.defineProperties @prototype, - effectiveModVersion: {get:@prototype.getEffectiveModVersion} - - # PageController Overrides ##################################################################### - - getMetaDescription: -> - return unless @model? - return Text.modDescription modName:@model.name - - getTitle: -> - return @model?.name - - # BaseController Overrides ##################################################################### - - onDidRender: -> - @adsenseController = @addChild AdsenseController, '.view__adsense' - - @$name = @$('.name') - @$byline = @$('.byline p') - @$description = @$('.description p') - @$documentationLink = @$('.documentation') - @$downloadLink = @$('.download') - @$homePageLink = @$('.homePage') - @$groupContainer = @$('.itemGroups') - @$titleImage = @$('.titleImage img') - @$titleImageContainer = @$('.titleImage') - @$tutorialsSection = @$('.tutorials') - @$tutorialsContainer = @$('.tutorials .panel') - @$versionSelector = @$('select.version') - - super - - refresh: -> - @adsenseController.fillAdPositions() - - if @model?.isLoaded and @effectiveModVersion?.isLoaded - @$byline.html "by #{@model.author}" - @$description.html @model.description - @$name.html @model.name - @$titleImage.attr 'src', Url.modIcon modSlug:@model.slug - - @show() - else - @hide() - - @_refreshLink @$homePageLink, @model?.homePageUrl - @_refreshLink @$documentationLink, @model?.documentationUrl - @_refreshLink @$downloadLink, @model?.downloadUrl - - @_refreshItemGroups() - @_refreshTutorials() - @_refreshVersions() - super - - # Backbone.View Methods ######################################################################## - - events: - 'change select.version': 'onVersionChanged' - - # Private Methods ############################################################################## - - _refreshItemGroups: -> - @_groupControllers ?= [] - groupIndex = 0 - modVersion = @effectiveModVersion - - if modVersion? - modVersion.eachGroup (group)=> - controller = @_groupControllers[groupIndex] - items = modVersion.allItemsInGroup group - if not controller? - controller = new ItemGroupController - imageLoader: @imageLoader - model: items - modPack: @modPack - title: if group is Item.Group.Other then 'Items' else group - - @_groupControllers.push controller - @$groupContainer.append controller.$el - controller.render() - else - controller.modVersion = modVersion - controller.model = items - controller.refresh() - groupIndex++ - - while @_groupControllers.length > groupIndex + 1 - @_groupControllers.pop().remove() - - _refreshLink: ($link, url)-> - if url? - $link.attr 'href', url - $link.removeClass 'hidden' - else - $link.addClass 'hidden' - - _refreshTutorials: -> - @_tutorialControllers ?= [] - index = 0 - tutorials = @model.tutorials - - if tutorials.length > 0 - for tutorial in tutorials - controller = @_tutorialControllers[index] - if not controller? - controller = new TutorialController model:tutorial - @_tutorialControllers.push controller - @$tutorialsContainer.append controller.$el - controller.render() - else - controller.model = tutorial - - index += 1 - - while @_tutorialControllers.length > index - @_tutorialControllers.pop().remove() - - @show @$tutorialsSection - else - @hide @$tutorialsSection - - _refreshVersions: -> - @$versionSelector.empty() - - if @model? - effectiveModVersion = @effectiveModVersion - versionCount = 0 - @model.eachModVersion (modVersion)=> - option = $("") - if modVersion is effectiveModVersion - option.attr 'selected', 'selected' - @$versionSelector.append option - versionCount++ - - if versionCount <= 1 - @$versionSelector.attr 'disabled', 'disabled' - else - @$versionSelector.removeAttr 'disabled' - - @show @$versionSelector - else - @hide @$versionSelector diff --git a/src/coffee/controllers/mod_selector_controller.coffee b/src/coffee/controllers/mod_selector_controller.coffee deleted file mode 100644 index 5486a3374..000000000 --- a/src/coffee/controllers/mod_selector_controller.coffee +++ /dev/null @@ -1,72 +0,0 @@ -### -Crafting Guide - mod_selector_controller.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' -BaseController = require './base_controller' -Mod = require '../models/mod' -_ = require 'underscore' -{Event} = require '../constants' -{RequiredMods} = require '../constants' -{Url} = require '../constants' - -######################################################################################################################## - -module.exports = class ModSelectorController extends BaseController - - constructor: (options={})-> - if not options.model? then throw new Error 'options.model is required' - options.templateName = 'mod_selector' - super options - - @_storage = options.storage - - # Event Methods ################################################################################ - - onVersionChanged: -> - @model.activeVersion = @$version.val() - - # BaseController Overrides ##################################################################### - - onDidRender: -> - @$version = @$('select') - @$nameLink = @$('.name a') - @$nameText = @$('.name p') - @$description = @$('.description p') - - super - - refresh: -> - if @model.activeVersion is Mod.Version.None - @$el.addClass 'disabled' - else - @$el.removeClass 'disabled' - - @$version.empty() - - if not (@model.slug in RequiredMods) - option = $("") - if @model.activeVersion is Mod.Version.None - option.attr 'selected', 'selected' - @$version.append option - - @model.eachModVersion (modVersion)=> - option = $("") - if modVersion is @model.activeModVersion - option.attr 'selected', 'selected' - @$version.append option - - @$nameLink.attr 'href', Url.mod(modSlug:@model.slug) - @$nameText.html @model.name - - @$description.html @model.description - - # Backbone.View Overrides ###################################################################### - - events: -> - return _.extend super, - 'change select': 'onVersionChanged' - 'click a': 'routeLinkClick' diff --git a/src/coffee/controllers/stack_controller.coffee b/src/coffee/controllers/stack_controller.coffee deleted file mode 100644 index 17a476b0f..000000000 --- a/src/coffee/controllers/stack_controller.coffee +++ /dev/null @@ -1,170 +0,0 @@ -### -Crafting Guide - stack_controller.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -BaseController = require './base_controller' -ImageLoader = require './image_loader' -_ = require 'underscore' -{Duration} = require '../constants' -{Event} = require '../constants' -{Key} = require '../constants' - -######################################################################################################################## - -### -Events: - change(this) - change:quantity(this, oldQuantity, newQuantity) - button:first(this, type) - button:second(this, type) -### -module.exports = class StackController extends BaseController - - @MAX_QUANTITY = 9999 - - constructor: (options={})-> - if not options.imageLoader? then throw new Error 'options.imageLoader is required' - if not options.model? then throw new Error 'options.model is required' - if not options.modPack? then throw new Error 'options.modPack is required' - - options.templateName = 'stack' - super options - - @editable = options.editable ?= false - @firstButtonType = options.firstButtonType ?= null - @imageLoader = options.imageLoader - @modPack = options.modPack - @secondButtonType = options.secondButtonType ?= null - @shouldEnableButton = options.shouldEnableButton ?= (model, button)-> true - - @modPack.on Event.change, => @tryRefresh() - - # Event Methods ################################################################################ - - onFirstButtonClicked: (event)-> - @trigger Event.button.first, this, @firstButtonType - return false - - onQuantityFieldBlur: -> - return unless @editable - - @$bubble.removeClass 'editing' - - oldQuantity = @_priorValue - quantityText = @$quantityField.val().trim() - if quantityText.length is 0 - newQuantity = oldQuantity - else if not quantityText.match /^[0-9]*$/ - newQuantity = 1 - else - newQuantity = parseInt quantityText, 10 - if _.isNaN newQuantity then newQuantity = 1 - - newQuantity = Math.min newQuantity, StackController.MAX_QUANTITY - newQuantity = Math.max 1, newQuantity - - @$quantityField.val "#{newQuantity}" - if newQuantity? and newQuantity isnt oldQuantity - @$bubble.removeClass 'error', Duration.snap - @$bubble.removeClass 'error-new', Duration.snap - - @model.quantity = newQuantity - @trigger Event.change + ':quantity', this, oldQuantity, newQuantity - @trigger Event.change, this - - onQuantityFieldChanged: -> - return unless @editable - - quantityText = @$quantityField.val().trim() - if not quantityText.match /^[0-9]*$/ - @$bubble.addClass 'error', 0 - @$bubble.addClass 'error-new', 0 - @$bubble.removeClass 'error-new', Duration.fast - else - @$bubble.removeClass 'error', Duration.snap - @$bubble.removeClass 'error-new', Duration.snap - - onQuantityFieldFocused: -> - - if @editable - @$bubble.addClass 'editing' - @_priorValue = @model.quantity - @$quantityField.val '' - else - @$quantityField.blur() - - onQuantityKeyUp: (event)-> - return unless @editable - - if event.which is Key.Return - @$quantityField.blur() - - onSecondButtonClicked: (event)-> - event.preventDefault() - @trigger Event.button.second, this, @secondButtonType - - # BaseController Overrides ##################################################################### - - onDidRender: -> - @$action = @$('.action') - @$bubble = @$('.bubble') - @$firstButton = @$('button.first') - @$image = @$('.icon img') - @$nameLink = @$('.name a') - @$quantityField = @$('.quantity input') - @$secondButton = @$('button.second') - super - - refresh: -> - if not @model? then throw new Error "must have a model to render" - - display = @modPack.findItemDisplay @model.itemSlug - - @imageLoader.load display.iconUrl, @$image - @$nameLink.html display.itemName - @$nameLink.attr 'href', display.itemUrl - - quantityText = if @model.quantity > 1000 then "#{@model.quantity / 1000}k" else "#{@model.quantity}" - @$quantityField.val quantityText - - @_updateButtonType @$firstButton, @firstButtonType - @_updateButtonType @$secondButton, @secondButtonType - - @$firstButton.prop('disabled', not @shouldEnableButton(@model, 1)) if @firstButtonType? - @$secondButton.prop('disabled', not @shouldEnableButton(@model, 2)) if @secondButtonType? - - if @editable - @$quantityField.removeAttr 'readonly' - @$bubble.addClass 'editable' - else - @$quantityField.attr 'readonly', 'readonly' - @$bubble.removeClass 'editable' - - super - - # Backbone.View Overrides ###################################################################### - - events: -> - return _.extend super, - 'blur .quantity input': 'onQuantityFieldBlur' - 'click .name a': 'routeLinkClick' - 'click button.first': 'onFirstButtonClicked' - 'click button.second': 'onSecondButtonClicked' - 'focus .quantity input': 'onQuantityFieldFocused' - 'input .quantity input': 'onQuantityFieldChanged' - 'keyup .quantity input': 'onQuantityKeyUp' - - # Private Methods ############################################################################## - - _updateButtonType: ($button, type)-> - for currentType in ['check', 'down', 'remove', 'up'] - $button.removeClass currentType - - if type? - $button.css 'display', null - $button.addClass type - else - $button.css 'display', 'none' diff --git a/src/coffee/controllers/tutorial_page_controller.coffee b/src/coffee/controllers/tutorial_page_controller.coffee deleted file mode 100644 index cfd1a6e4c..000000000 --- a/src/coffee/controllers/tutorial_page_controller.coffee +++ /dev/null @@ -1,152 +0,0 @@ -### -Crafting Guide - tutorial_page_controller.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -AdsenseController = require './adsense_controller' -BaseController = require './base_controller' -MarkdownSectionController = require './markdown_section_controller' -VideoController = require './video_controller' -{Duration} = require '../constants' -{Event} = require '../constants' -{Url} = require '../constants' - -######################################################################################################################## - -module.exports = class TutorialPageController extends BaseController - - constructor: (options={})-> - if not options.modSlug? then throw new Error 'options.modSlug is required' - if not options.tutorialSlug? then throw new Error 'options.tutorialSlug is required' - if not options.modPack? then throw new Error 'options.modPack is required' - - options.model ?= null - options.templateName = 'tutorial_page' - super options - - @modPack = options.modPack - @imageLoader = options.imageLoader - @modSlug = options.modSlug - @tutorialSlug = options.tutorialSlug - - @modPack.on Event.change, => @_resolveTutorial() - @_resolveTutorial() - - # BaseController Overrides ##################################################################### - - onDidRender: -> - @adsenseController = @addChild AdsenseController, '.view__adsense', model:'sidebar_skyscraper' - - @$byline = @$('.byline') - @$bylineLink = @$('.byline a') - @$name = @$('.name') - @$officialLink = @$('a.officialPage') - @$sectionsContainer = @$('.sections') - @$title = @$('h1.name') - @$titleImage = @$('.titleImage img') - @$videosSection = @$('.videos') - @$videosSectionTitle = @$('.videos h2') - @$videosSectionPanel = @$('.videos .panel') - super - - refresh: -> - if @model? and @model.isLoaded - @_refreshByline() - @_refreshOfficialUrl() - @_refreshSections() - @_refreshTitle() - @_refreshVideos() - - @show() - else - @hide() - - super - - # Private Methods ############################################################################## - - _refreshByline: -> - @$bylineLink.html @modPack.getMod(@modSlug).name - @$bylineLink.attr 'href', Url.mod modSlug:@modSlug - - _refreshOfficialUrl: -> - if @model.officialUrl? - @$officialLink.attr 'href', @model.officialUrl - @show @$officialLink - else - @hide @$officialLink - - _refreshTitle: -> - @$title.html @model.name - @$titleImage.attr 'src', Url.tutorialIcon modSlug:@modSlug, tutorialSlug:@tutorialSlug - - _refreshSections: -> - @_sectionControllers ?= [] - index = 0 - - for section in @model.sections - controller = @_sectionControllers[index] - if not controller? - controller = new MarkdownSectionController title:section.title, model:section.content, modPack:@modPack - @_sectionControllers.push controller - @$sectionsContainer.append controller.$el - controller.render() - else - controller.title = section.title - controller.model = section.model - controller.refresh() - - controller.imageBase = Url.tutorialImageDir modSlug:@modSlug, tutorialSlug:@tutorialSlug - index += 1 - - while @_sectionControllers.length > index - @_sectionController.pop().remove() - - _refreshVideos: -> - @_videoControllers ?= [] - index = 0 - - videos = @model?.videos or [] - if videos? and videos.length > 0 - @$videosSectionTitle.html if videos.length is 1 then 'Video' else 'Videos' - - for video in videos - controller = @_videoControllers[index] - if not controller? - controller = new VideoController model:video - @_videoControllers.push controller - @$videosSectionPanel.append controller.$el - controller.render() - else - controller.model = video - - index += 1 - - @show @$videosSection - else - @hide @$videosSection - - while @_videoControllers.length > index - @_videoControllers.pop().remove() - - _resolveTutorial: -> - return if @model? - - mod = @modPack.getMod @modSlug - if not mod? - logger.error => "cannot find the mod for: #{@modSlug}" - router.navigate '/', trigger:true - return - - if not mod.isLoaded - mod.fetch() - return - - @model = mod.getTutorial @tutorialSlug - if not @model? - logger.error => "mod #{@modSlug} doesn't have a tutorial for: #{@tutorialSlug}" - return - - @model.fetch() diff --git a/src/coffee/crafting_guide_router.coffee b/src/coffee/crafting_guide_router.coffee deleted file mode 100644 index ffdbe9501..000000000 --- a/src/coffee/crafting_guide_router.coffee +++ /dev/null @@ -1,288 +0,0 @@ -### -Crafting Guide - router.coffee - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' -BrowsePageController = require './controllers/browse_page_controller' -ConfigurePageController = require './controllers/configure_page_controller' -CraftPageController = require './controllers/craft_page_controller' -HeaderController = require './controllers/header_controller' -HomePageController = require './controllers/home_page_controller' -ImageLoader = require './controllers/image_loader' -ItemPageController = require './controllers/item_page_controller' -ItemSlug = require './models/item_slug' -LoginPageController = require './controllers/login_page_controller' -Mod = require './models/mod' -ModPack = require './models/mod_pack' -ModPageController = require './controllers/mod_page_controller' -Storage = require './models/storage' -TutorialPageController = require './controllers/tutorial_page_controller' -UrlParams = require './url_params' -User = require './models/user' -_ = require 'underscore' -backbone = require 'backbone' -{DefaultMods} = require './constants' -{Duration} = require './constants' -{Event} = require './constants' -{Opacity} = require './constants' -{ProductionEnvs} = require './constants' -{Url} = require './constants' - -######################################################################################################################## - -module.exports = class CraftingGuideRouter extends backbone.Router - - constructor: (options={})-> - @_lastReported = null - @_page = null - @_pageControllers = {} - @_postLoginUrl = Url.root - @_user = null - super options - - @client = options.client - @imageLoader = new ImageLoader defaultUrl:'/images/unknown.png' - @modPack = new ModPack - @storage = new Storage storage:window.localStorage - - @_defaultOptions = client:@client, imageLoader:@imageLoader, modPack:@modPack, storage:@storage, user:@_user - @on Event.change + ':user', => @_defaultOptions.user = @_user - - @headerController = new HeaderController _.extend {el:'.view__header'}, @_defaultOptions - @headerController.render() - @on Event.change + ':user', => @headerController.user = @user - - # Public Methods ############################################################################### - - loadDefaultModPack: -> - makeResponder = (m)-> return -> - m.activeModVersion.fetch() if m.activeModVersion? - - for modSlug, modData of DefaultMods - mod = new Mod slug:modSlug - mod.on Event.change + ':activeModVersion', makeResponder mod - @storage.register "mod:#{mod.slug}", mod, 'activeVersion', modData.defaultVersion - mod.fetch() - - @modPack.addMod mod - - if global.env isnt 'prerender' - @modPack.once Event.sync, -> - $('.page').css 'max-height', '' - $('.page-loading').remove() - - loadCurrentUser: -> - @client.fetchCurrentUser() - .then (response)=> - userData = response.json?.data?.user - @user = new User userData if userData? - .catch (error)=> - if error.response.statusCode isnt 401 - logger.error "Failed to get current user: #{error}" - else - logger.info "User is not logged in" - .done() - - login: -> - @storage.store 'post-login-url', window.location.pathname - @navigate Url.login(), trigger:true - - resumeAfterLogin: -> - url = @storage.load 'post-login-url' - url = if (not url? or url is 'null') then Url.root() else url - @navigate url, trigger:true - @storage.store 'post-login-url', null - - # Property Methods ############################################################################# - - getUser: -> - return @_user - - setUser: (newUser)-> - oldUser = @_user - return if newUser is oldUser - - @_user = newUser - logger.info -> "User changed to: #{newUser}" - - @trigger Event.change + ':user', this, oldUser, newUser - @trigger Event.change, this - - if @_controller? then @_controller.user = newUser - - Object.defineProperties @prototype, - user: {get:@prototype.getUser, set:@prototype.setUser} - - # Backbone.Router Overrides #################################################################### - - navigate: -> - super - @_recordPageView() - - routes: - '': 'route__home' - '/': 'route__home' - '/index.html': 'route__home' - - 'browse': 'route__browse' - 'browse/': 'route__browse' - 'browse/index.html': 'route__browse' - - 'browse/:modSlug': 'route__browseMod' - 'browse/:modSlug/': 'route__browseMod' - 'browse/:modSlug/index.html': 'route__browseMod' - - 'browse/:modSlug/:itemSlug': 'route__browseModItem' - 'browse/:modSlug/:itemSlug/': 'route__browseModItem' - 'browse/:modSlug/:itemSlug/index.html': 'route__browseModItem' - - 'browse/:modSlug/tutorials/:tutorialSlug': 'route__browseTutorial' - 'browse/:modSlug/tutorials/:tutorialSlug/': 'route__browseTutorial' - 'browse/:modSlug/tutorials/:tutorialSlug/index.html': 'route__browseTutorial' - - 'configure': 'route__configure' - 'configure/': 'route__configure' - 'configure/index.html': 'route__configure' - - 'craft': 'route__craft' - 'craft/': 'route__craft' - 'craft/index.html': 'route__craft' - - 'craft/:text': 'route__craft' - 'craft/:text/': 'route__craft' - 'craft/:text/index.html': 'route__craft' - - 'login': 'route__login' - 'login/': 'route__login' - 'login/index.html': 'route__login' - - 'item/:itemSlug': 'deprecated__item' - 'crafting/(:text)': 'deprecated__crafting' - 'mod/:modSlug': 'deprecated__mod' - 'mod/:modSlug/:itemSlug': 'deprecated__modItem' - - # Route Methods ################################################################################ - - route__home: -> - params = new UrlParams recipeName:{type:'string'}, count:{type:'integer'} - if params.recipeName? - @deprecated__v1_root params - return - - @_setPage 'home', new HomePageController _.extend {}, @_defaultOptions - - route__browse: -> - @_setPage 'browse', new BrowsePageController _.extend {}, @_defaultOptions - - route__browseMod: (modSlug)-> - controller = new ModPageController _.extend {}, @_defaultOptions - controller.model = @modPack.getMod modSlug - @_setPage 'browseMod', controller - - route__browseModItem: (modSlug, itemSlug)-> - slug = new ItemSlug modSlug, itemSlug - controller = new ItemPageController _.extend {itemSlug:slug}, @_defaultOptions - @_setPage 'browseModItem', controller - - route__browseTutorial: (modSlug, tutorialSlug)-> - controller = new TutorialPageController _.extend {modSlug:modSlug, tutorialSlug:tutorialSlug}, @_defaultOptions - @_setPage 'browseTutorial', controller - - route__configure: -> - @_setPage 'configure', new ConfigurePageController _.extend {}, @_defaultOptions - - route__craft: (text)-> - controller = new CraftPageController _.extend {}, @_defaultOptions - controller.model.params = inventoryText:text - @_setPage 'craft', controller - - route__login: -> - params = new UrlParams code:{type:'string'}, state:{type:'string'} - controller = new LoginPageController _.extend {params:params}, @_defaultOptions - @_setPage 'login', controller - - # Deprecated Route Methods ##################################################################### - - deprecated__crafting: (text)-> - controller = new CraftPageController _.extend {}, @_defaultOptions - controller.model.params = inventoryText:text - @_setPage 'crafting', controller - - deprecated__item: (itemSlug)-> - controller = new ItemPageController _.extend {itemSlug:ItemSlug.slugify(itemSlug)}, @_defaultOptions - @_setPage 'item', controller - - deprecated__modItem: (modSlug, itemSlug)-> - slug = new ItemSlug modSlug, itemSlug - controller = new ItemPageController _.extend {itemSlug:slug}, @_defaultOptions - @_setPage 'item', controller - - deprecated__mod: (modSlug)-> - controller = new ModPageController _.extend {}, @_defaultOptions - controller.model = @modPack.getMod modSlug - @_setPage 'mod', controller - - deprecated__v1_root: (params)-> - text = '' - if params.recipeName? - if params.count? and params.count > 1 - text = "#{params.count}.#{_.slugify(params.recipeName)}" - else - text = _.slugify params.recipeName - - @navigate Url.crafting(inventoryText:text), trigger:true - - # Private Methods ############################################################################## - - _recordPageView: -> - pathname = window.location.pathname - - if global.env is 'production' and ga? - logger.info -> "Recording GA page view: #{pathname}" - ga 'send', 'pageview', pathname - else - logger.info -> "Suppressing GA page view: #{pathname}" - - _setPage: (page, controller)-> - return if @_controller is controller - - logger.info -> "changing to page controller: #{controller.constructor.name}" - @headerController.model = page - - showDuration = Duration.normal - switchToNextController = (event)=> - @_controller.unrender() if @_controller? - @_resetGlobals() - - @_page = page - @_controller = controller - - $pageContent = $('.page') - $pageContent.attr 'class', 'page hideable hidden' - - window.scrollTo 0, 0 - - controller.user = @user - controller.onWillShow() - controller.$el = $pageContent - controller.render() - controller.show() - - if @_controller? - @_controller.once Event.animate.hide.finish, switchToNextController - @_controller.hide() - else - switchToNextController() - - _resetGlobals: -> - if global.env in ProductionEnvs - for key, value of global - if key.indexOf('google') isnt -1 - delete global[key] - - delete global.adsByGoogle - $('script[src="//pagead2.googlesyndication.com/pagead/js/adsbygoogle.js"]').remove() - $('body').append('') diff --git a/src/coffee/index.coffee b/src/coffee/index.coffee deleted file mode 100644 index 492aa961a..000000000 --- a/src/coffee/index.coffee +++ /dev/null @@ -1,20 +0,0 @@ -### -Crafting Guide - index.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -_ = require 'underscore' -mixins = require './underscore_mixins' - -######################################################################################################################## - -_.mixin mixins - -module.exports = - constants: require './constants' - Mod: require './models/mod' - ModParser: require './models/mod_parser' - ModVersion: require './models/mod_version' - ModVersionParser: require './models/mod_version_parser' diff --git a/src/coffee/models/email_client.coffee b/src/coffee/models/email_client.coffee deleted file mode 100644 index e76eed147..000000000 --- a/src/coffee/models/email_client.coffee +++ /dev/null @@ -1,62 +0,0 @@ -### -Crafting Guide - email_client.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -$ = require 'jquery' -_ = require 'underscore' -util = require 'util' -w = require 'when' - -######################################################################################################################## - -module.exports = class EmailClient - - constructor: -> - @baseUrl = 'https://mandrillapp.com:443/api/1.0' - @key = 'zaERWIuTVJaq0seCjjgVqw' - - # Public Methods ############################################################################### - - send: (options={})-> - options.body ?= "(no body)" - options.fromAddress ?= "info@crafting-guide.com" - options.fromName ?= "Crafting Guide Website" - options.subject ?= "(no subject)" - options.toAddress ?= "info@crafting-guide.com" - options.toName ?= "Crafting Guide" - - body = - key: @key - message: - from_email: options.fromAddress - from_name: options.fromName - subject: options.subject - text: options.body - to: [ email:options.toAddress, name:options.toName, type:'to' ] - - logger.info -> "sending email: #{util.inspect(body)}" - - w.promise (resolve, reject)=> - - onSuccess = (data, status, request)-> - logger.info -> "sending email result: #{util.inspect(data)}, status:#{status}" - data = if _.isArray data then data[0] else data - if data.status isnt "sent" - reject status:data.status, message:data.reject_reason - else - resolve status:data.status - - onError = (request, status, error)-> - logger.error -> "sending email failed: #{status}, error:#{error}" - reject status:status, message:error - - $.ajax "#{@baseUrl}/messages/send.json", - cache: false - data: body - dataType: 'json' - error: onError - success: onSuccess - type: 'POST' diff --git a/src/coffee/models/name_finder.coffee b/src/coffee/models/name_finder.coffee deleted file mode 100644 index 8dbf7d824..000000000 --- a/src/coffee/models/name_finder.coffee +++ /dev/null @@ -1,68 +0,0 @@ -### -Crafting Guide - name_finder.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -######################################################################################################################## - -module.exports = class NameFinder - - constructor: (modPack, options={})-> - if not modPack? then throw new Error 'modPack is required' - - options.includeGatherable ?= false - options.includeDisabledMods ?= false - options.limit ?= 25 - - @includeDisabledMods = options.includeDisabledMods - @includeGatherable = options.includeGatherable - @limit = options.limit - @modPack = modPack - @names = [] - @_nameMap = {} - - # Public Methods ############################################################################### - - search: (nameHint='')-> - nameHint = null if nameHint.trim() is '' - nameHint = nameHint.toLowerCase() if nameHint? - names = @_findNames nameHint - - names.sort (a, b)-> - c = a.mod.compareTo b.mod - if c isnt 0 then return c - - return 0 if a.label is b.label - return if a.label < b.label then -1 else +1 - - names = names[0...@limit] - - return names - - # Private Methods ############################################################################## - - _findNames: (nameHint=null)-> - names = [] - nameMap = {} - hintRegex = new RegExp(nameHint, 'i') if nameHint? - - @modPack.eachMod (mod)=> - return unless mod.enabled or @includeDisabledMods - - mod.eachName (name, itemSlug)=> - return if nameMap[name]? - - if not @includeGatherable - item = mod.findItem itemSlug - return unless item? and item.isCraftable - - scanName = "#{mod.name} : #{name}" - if hintRegex? - return unless hintRegex.test scanName - - nameMap[name] = name - names.push value:name, label:scanName, mod:mod - - return names diff --git a/src/coffee/polyfill.coffee b/src/coffee/polyfill.coffee deleted file mode 100644 index 1ae605ef5..000000000 --- a/src/coffee/polyfill.coffee +++ /dev/null @@ -1,13 +0,0 @@ -### -Crafting Table - polyfill.coffee - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -### - -######################################################################################################################## - -if not Array.prototype.clear? - Object.defineProperty Array.prototype, 'clear', value:-> - @splice 0, @length - return this diff --git a/src/common/constants.coffee b/src/common/constants.coffee new file mode 100644 index 000000000..d5e035ec7 --- /dev/null +++ b/src/common/constants.coffee @@ -0,0 +1,141 @@ +# +# Crafting Guide - constants.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +######################################################################################################################## + +exports.adsense = adsense = {} +adsense.clientId = 'ca-pub-6593013914878730' +adsense.skyscraper = {} +adsense.skyscraper.height = 600 +adsense.skyscraper.width = 160 +adsense.skyscraper.margin = 24 +adsense.slotIds = ['7613920409', '9574673605', '3388539204'] + +exports.defaultMods = defaultMods = {} +defaultMods.minecraft = { defaultVersion: '1.7.10' } # Minecraft must be first + +defaultMods.advanced_solar_panels = { defaultVersion: '3.5.1' } +defaultMods.applied_energistics_2 = { defaultVersion: 'rv1-stable-1' } +defaultMods.big_reactors = { defaultVersion: '0.4.2A2' } +defaultMods.buildcraft = { defaultVersion: '6.4.6' } +defaultMods.computercraft = { defaultVersion: '1.74' } +defaultMods.enderio = { defaultVersion: '2.2.7.325' } +defaultMods.ender_storage = { defaultVersion: '1.4.5.29' } +defaultMods.extra_cells = { defaultVersion: '2.2.73b129' } +defaultMods.extra_utilities = { defaultVersion: '1.2.2' } +defaultMods.forestry = { defaultVersion: '3.4.0.7' } +defaultMods.forge_multipart = { defaultVersion: '1.2.0.345' } +defaultMods.galacticraft = { defaultVersion: '3.0.12.404' } +defaultMods.hydraulicraft = { defaultVersion: '2.1.242' } +defaultMods.ic2_classic = { defaultVersion: 'none' } +defaultMods.industrial_craft_2 = { defaultVersion: '2.2.663' } +defaultMods.iron_chests = { defaultVersion: '6.0.62.742' } +defaultMods.jabba = { defaultVersion: '1.2.1a' } +defaultMods.mekanism = { defaultVersion: '7.1.1.127' } +defaultMods.minefactory_reloaded = { defaultVersion: '2.8.0RC8-86' } +defaultMods.modular_powersuits = { defaultVersion: '0.11.0-300-thermal-expansion' } +defaultMods.opencomputers = { defaultVersion: '1.5.22' } +defaultMods.railcraft = { defaultVersion: '9.5.0' } +defaultMods.simply_jetpacks = { defaultVersion: '1.4.1' } +defaultMods.solar_flux = { defaultVersion: '0.5b' } +defaultMods.storage_drawers = { defaultVersion: '1.7.10-1.6.2' } +defaultMods.thermal_dynamics = { defaultVersion: '1.0.0RC7-98' } +defaultMods.thermal_expansion = { defaultVersion: '4.0.0B8-23' } + +exports.duration = duration = {} +duration.snap = 100 +duration.fast = 200 +duration.normal = 400 +duration.slow = 1200 + +exports.event = event = {} +event.add = 'add' # collection, item... +event.button = {} +event.button.complete = 'button:complete' # controller +event.button.first = 'button:first' # controller, buttonType +event.button.second = 'button:second' # controller, buttonType +event.change = 'change' # model +event.click = 'click' # event +event.load = {} +event.load.started = 'load:started' # controller, url +event.load.succeeded = 'load:succeeded' # controller, book +event.load.failed = 'load:failed' # controller, error message +event.load.finished = 'load:finished' # controller +event.remove = 'remove' # collection, item... +event.request = 'request' # model +event.route = 'route' +event.sort = 'sort' +event.sync = 'sync' # model, response + +exports.gitHub = gitHub = {} +gitHub.file = {} +gitHub.file.itemDescription = {} +gitHub.file.itemDescription.fileName = _.template "item.cg" +gitHub.file.itemDescription.path = _.template "/data/<%= modSlug %>/items/<%= itemSlug %>" + +exports.key = key = {} +key.enter = 13 +key.return = 13 +key.escape = 27 +key.upArrow = 38 +key.downArrow = 40 + +exports.limits = limits = {} +limits.maximumGraphSize = 5000 +limits.maximumPlanCount = 5000 + +exports.login = login = {} +login.authorizeUrl = _.template "https://github.com/login/oauth/authorize" + + "?client_id=<%= clientId %>&scope=public_repo&state=<%= state %>" +login.clientIds = + 'local': '20afe4dbe75464a8cf36' + 'production': 'ce71be7f66926ff6ff38' + +exports.modelState = modelState = {} +modelState.unloaded = 'unloaded' +modelState.loading = 'loading' +modelState.loaded = 'loaded' +modelState.failed = 'failed' + +exports.opacity = opacity = {} +opacity.hidden = 1e-6 +opacity.shown = 1 + +exports.productionEnvs = [ 'staging', 'production' ] + +exports.requiredMods = [ 'minecraft' ] + +exports.server = {} +exports.server.defaultPort = 8080 + +exports.text = text = {} +text.browseDescription = _.template 'Browse through complete item listings for over a dozen top mods and use the interactive crafting planner for step-by-step instructions' +text.configDescription = _.template 'Configure the interactive crafting planner for your exact modpack and get step-by-step instructions for any item in your world' +text.craftDescription = _.template 'Build anything in your Minecraft mod pack with a full list of materials and step-by-step instructions using our interactive crafting planner' +text.homeDescription = _.template 'Find everything you need to know about your Minecraft mod pack and use the interactive crafting planner for step-by-step instructions and full lists of materials' +text.itemDescription = _.template 'Make <%= itemName %> and the rest of <%= modName %> easy and use the interactive crafting planner for step-by-step instructions' +text.modDescription = _.template 'Make <%= modName %> easy with tutorials, videos, and a full item listing along with an interactive crafting planner for step-by-step instructions' +text.title = _.template 'Minecraft Crafting Guide' +text.titleWithText = _.template '<%= text %> | Minecraft Crafting Guide' + +exports.url = url = {} +url.crafting = _.template "/craft/<%= inventoryText %>" +url.item = _.template "/browse/<%= modSlug %>/<%= itemSlug %>/" +url.itemData = _.template "/data/<%= modSlug %>/items/<%= itemSlug %>/item.cg" +url.itemIcon = _.template "/data/<%= modSlug %>/items/<%= itemSlug %>/icon.png" +url.itemImageDir = _.template "/data/<%= modSlug %>/items/<%= itemSlug %>" +url.login = _.template "/login" +url.mod = _.template "/browse/<%= modSlug %>/" +url.modData = _.template "/data/<%= modSlug %>/mod.cg" +url.modIcon = _.template "/data/<%= modSlug %>/icon.png" +url.modVersionData = _.template "/data/<%= modSlug %>/versions/<%= modVersion %>/mod-version.cg" +url.root = _.template "/" +url.tutorial = _.template "/browse/<%= modSlug %>/tutorials/<%= tutorialSlug %>/" +url.tutorialData = _.template "/data/<%= modSlug %>/tutorials/<%= tutorialSlug %>/tutorial.cg" +url.tutorialIcon = _.template "/data/<%= modSlug %>/tutorials/<%= tutorialSlug %>/icon.png" +url.tutorialIcon = _.template "/data/<%= modSlug %>/tutorials/<%= tutorialSlug %>/icon.png" +url.tutorialImageDir = _.template "/data/<%= modSlug %>/tutorials/<%= tutorialSlug %>" diff --git a/src/common/fs.extensions.coffee b/src/common/fs.extensions.coffee new file mode 100644 index 000000000..602e6dada --- /dev/null +++ b/src/common/fs.extensions.coffee @@ -0,0 +1,22 @@ +# +# Crafting Guide - fs.extensions.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +fs = require 'fs' +path = require 'path' + +######################################################################################################################## + +fs.rmdirRfSync ?= (filePath)-> + stat = fs.statSync filePath + if stat.isDirectory() + for childFileName in fs.readdirSync filePath + fs.rmdirRfSync path.join filePath, childFileName + fs.rmdirSync filePath + else + fs.unlinkSync filePath + +module.exports = fs diff --git a/src/common/fs.extensions.test.coffee b/src/common/fs.extensions.test.coffee new file mode 100644 index 000000000..ed4e0e2ee --- /dev/null +++ b/src/common/fs.extensions.test.coffee @@ -0,0 +1,52 @@ +# +# Crafting Guide - fs.extensions.test.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +fs = require './fs.extensions' + +######################################################################################################################## + +describe 'fs.extensions.coffee', -> + + describe 'rmdirRfSync', -> + + beforeEach -> + fs.mkdirSync '.tmp' + + afterEach -> + fs.rmdirRfSync '.tmp' + + it 'can remove a single file', -> + fs.writeFileSync '.tmp/alpha' + + fs.rmdirRfSync '.tmp/alpha' + func = -> fs.statSync '.tmp/alpha' + expect(func).to.throw Error, 'no such file' + + it 'can remove an empty directory', -> + fs.mkdirSync '.tmp/alpha' + + fs.rmdirRfSync '.tmp/alpha' + func = -> fs.statSync '.tmp/alpha' + expect(func).to.throw Error, 'no such file' + + it 'can remove a directory with a file', -> + fs.mkdirSync '.tmp/alpha' + fs.writeFileSync '.tmp/bravo' + + fs.rmdirRfSync '.tmp/alpha' + func = -> fs.statSync '.tmp/alpha' + expect(func).to.throw Error, 'no such file' + + it 'can remove a nested sub-directory with a file', -> + fs.mkdirSync '.tmp/alpha' + fs.writeFileSync '.tmp/bravo' + fs.mkdirSync '.tmp/alpha/charlie' + fs.writeFileSync '.tmp/alpha/charlie/delta' + + fs.rmdirRfSync '.tmp/alpha' + func = -> fs.statSync '.tmp/alpha' + expect(func).to.throw Error, 'no such file' diff --git a/src/coffee/underscore_mixins.coffee b/src/common/underscore.coffee similarity index 64% rename from src/coffee/underscore_mixins.coffee rename to src/common/underscore.coffee index a59d38b01..af599c914 100644 --- a/src/coffee/underscore_mixins.coffee +++ b/src/common/underscore.coffee @@ -1,16 +1,14 @@ -### -Crafting Guide - underscore_mixins.coffee +# +# Crafting Guide - underscore.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -### +module.exports = _ = require 'underscore' -_ = require 'underscore' -{stringMixins} = require 'crafting-guide-common' - -######################################################################################################################## - -module.exports = _ +_.mixin require 'underscore.inflections' +_.mixin require('crafting-guide-common').stringMixins _.mixin parseMarkdown: (text)-> @@ -37,5 +35,3 @@ _.mixin parts = [ null, parts[0] ] return parts - -_.mixin stringMixins diff --git a/src/jade/app.jade b/src/jade/app.jade deleted file mode 100644 index e0920ac0d..000000000 --- a/src/jade/app.jade +++ /dev/null @@ -1,32 +0,0 @@ -//- -//- Crafting Guide - app.jade -//- -//- Copyright (c) 2014-2015 by Redwood Labs -//- All rights reserved. -//- - -doctype html -html - head - title The Ultimate Minecraft Crafting Guide - meta(charset="UTF-8") - link(href="/images/favicon.png", rel="icon", type="image/png") - - block styles - link(rel="stylesheet", type="text/css", href="/css/main.css") - - body - block body - .view__feedback - .view__screen - - .content - include ./includes/_header.jade - .page.hideable(style="max-height: 0") - .page-loading: img(src="/images/wait.gif") - include ./includes/_footer.jade - - block scripts - include ./includes/_standard_scripts.jade - include ./includes/_google_adsense.jade - include ./includes/_google_analytics.jade diff --git a/src/jade/includes/_footer.jade b/src/jade/includes/_footer.jade deleted file mode 100644 index 175cb2599..000000000 --- a/src/jade/includes/_footer.jade +++ /dev/null @@ -1,36 +0,0 @@ -//- -//- Crafting Guide - _footer.jade -//- -//- Copyright (c) 2014-2015 by Redwood Labs -//- All rights reserved. -//- - -.view__footer - .divider.top - .left - h2: p About - p. - Crafting Guide gives step-by-step tutorials for making anything in Minecraft or its many mods. Just say what - you'd like to make, what you already have, it will do the rest, giving you a list of raw materials you need - to collect and step-by-step instructions of how much to make of which items in the proper order. You can - even ask it to include the materials and instructions for all the tools you'll need along the way! - - .center - h2: p Donate - p Crafting Guide is free for all, but if you find it helpful, donations in any amount are gratefully accepted. - .action - form(action="https://www.paypal.com/cgi-bin/webscr", class="centered", method="post", target="_top") - input(type="hidden", name="cmd", value="_s-xclick") - input(type="hidden", name="hosted_button_id", value="GCB2TYZJYLAE6") - input(type="image", src="https://www.paypalobjects.com/en_US/i/btn/btn_donate_LG.gif", border="0", - name="submit" alt="PayPal - The safer, easier way to pay online!") - img(src="https://www.paypalobjects.com/en_US/i/scr/pixel.gif", width="1", height="1") - .right - h2: p Get Involved - p Crafting Guide is completely open-source, and you can help! Whether you want to write a recipe book (all - | simple JSON), or implement new features, just head over to GitHub to get started. - .action - iframe(src="http://ghbtns.com/github-btn.html?user=andrewminer&repo=crafting-guide&type=fork&size=large", - allowtransparency="true", frameborder="0", scrolling="0", width="100", height="32") - - .divider.bottom diff --git a/src/jade/includes/_header.jade b/src/jade/includes/_header.jade deleted file mode 100644 index 5add36f05..000000000 --- a/src/jade/includes/_header.jade +++ /dev/null @@ -1,33 +0,0 @@ -//- -//- Crafting Guide - _header.jade -//- -//- Copyright (c) 2014-2015 by Redwood Labs -//- All rights reserved. -//- - -.view__header - h1 - a.logo(href="/"): img(src="/images/workbench_front.png") - p Minecraft Crafting Guide - - .addthis_sharing_toolbox - .divider.bottom - .login - span.name - a(href="/login/") Login - - .navBar - a(data-page="home", href="/") - p Home - .dot - a(data-page="configure", href="/configure/") - p Configure - .dot - a(data-page="browse", href="/browse/") - p Browse - .dot - a(data-page="craft", href="/craft/") - p Craft - .dot - - .view__item_selector.search: p find an item... diff --git a/src/jade/includes/_standard_scripts.jade b/src/jade/includes/_standard_scripts.jade deleted file mode 100644 index c7dfc7ff9..000000000 --- a/src/jade/includes/_standard_scripts.jade +++ /dev/null @@ -1,8 +0,0 @@ -//- -//- Crafting Guide - _standard_scripts.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -script(src="/js/main.js") diff --git a/src/jade/templates/adsense_sidebar_skyscraper.jade b/src/jade/templates/adsense_sidebar_skyscraper.jade deleted file mode 100644 index d3d326961..000000000 --- a/src/jade/templates/adsense_sidebar_skyscraper.jade +++ /dev/null @@ -1,8 +0,0 @@ -//- -//- Crafting Guide - _adsense_sidebar_skyscraper.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__adsense diff --git a/src/jade/templates/browse_page.jade b/src/jade/templates/browse_page.jade deleted file mode 100644 index 8f5fd4b52..000000000 --- a/src/jade/templates/browse_page.jade +++ /dev/null @@ -1,14 +0,0 @@ -//- -//- Crafting Guide - browse_page.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__browse_page - .sidebar - ins.view__adsense - - .mainBody - h2: p Active Mods - .mods diff --git a/src/jade/templates/configure_page.jade b/src/jade/templates/configure_page.jade deleted file mode 100644 index 4c4485eaf..000000000 --- a/src/jade/templates/configure_page.jade +++ /dev/null @@ -1,13 +0,0 @@ -//- -//- Crafting Guide - configure_page.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__configure_page - .sidebar - .view__adsense - - .mainBody - .view__mod_pack diff --git a/src/jade/templates/craft_page.jade b/src/jade/templates/craft_page.jade deleted file mode 100644 index b5d88f0a8..000000000 --- a/src/jade/templates/craft_page.jade +++ /dev/null @@ -1,45 +0,0 @@ -//- -//- Crafting Guide - landing_page.jade -//- -//- Copyright (c) 2014-2015 by Redwood Labs -//- All rights reserved. -//- - -.view__craft_page - .sidebar - ins.view__adsense - - .mainBody - - .want.section - h2 Items to Make - .panel - .view__inventory.large.editable - - .have.section - h2 Already in Inventory - .panel - .view__inventory.large - - .view__craftsman_working.section - - .need.section.hideable.hidden - h2 Need to Gather - .panel - .view__inventory.large - - .steps.section.hideable.hidden - h2 Steps - .panel - - .instructions.section - h2 Instructions - .panel - p. - Welcome to the Craft page. Here you can get detailed instructions for making any item in your - current mod pack (use the Configure page to change it). Making a crafting - plan is very simple: - ol - li Click the "add an item..." button to choose items to craft - li Use the button to mark any items you already possess - li Use the button to complete any step if you already have that item diff --git a/src/jade/templates/crafting_grid.jade b/src/jade/templates/crafting_grid.jade deleted file mode 100644 index 4312a9c24..000000000 --- a/src/jade/templates/crafting_grid.jade +++ /dev/null @@ -1,20 +0,0 @@ -//- -//- Crafting Guide - crafting_grid.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -table.view__crafting_grid - tr - td: .view__slot - td: .view__slot - td: .view__slot - tr - td: .view__slot - td: .view__slot - td: .view__slot - tr - td: .view__slot - td: .view__slot - td: .view__slot diff --git a/src/jade/templates/crafting_table.jade b/src/jade/templates/crafting_table.jade deleted file mode 100644 index b4aefa5d0..000000000 --- a/src/jade/templates/crafting_table.jade +++ /dev/null @@ -1,19 +0,0 @@ -//- -//- Crafting Guide - crafting_table.jade -//- -//- Copyright (c) 2014-2015 by Redwood Labs -//- All rights reserved. -//- - -.view__crafting_table - h2 - img(src="/images/workbench_top.png") - p Crafting Plan - - .panel - .prev - .view__minimal_recipe - .next - - .problem.hideable - a report a problem diff --git a/src/jade/templates/feedback.jade b/src/jade/templates/feedback.jade deleted file mode 100644 index 9ffaa006a..000000000 --- a/src/jade/templates/feedback.jade +++ /dev/null @@ -1,19 +0,0 @@ -//- -//- Crafting Guide - feedback.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__feedback - input(name="name", placeholder="name (optional)") - input(name="email", placeholder="email (optional)") - - label(name="comment") Comment: - textarea(name="comment") - button(name="send") send - .error.hideable.hidden: p Sending failed. Please try again later. - - .label - img(src="/images/paper.png") - p Feedback \ No newline at end of file diff --git a/src/jade/templates/home_page.jade b/src/jade/templates/home_page.jade deleted file mode 100644 index aa4214668..000000000 --- a/src/jade/templates/home_page.jade +++ /dev/null @@ -1,167 +0,0 @@ -//- -//- Crafting Guide - home_page.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__home_page - .sidebar - .view__adsense - - .mainBody - .section - h2 Welcome! - .panel - .entry - p.intro. - Crafting Guide is the ultimate resource for Minecraft. Whether you're punching trees or building - reactors, you'll find Crafting Guide indispensable. - ul - li.intro Can't remember the recipe for a BuildCraft Quarry? - li.intro Curious to see all the blocks added by Railcraft? - li.intro Want step-by-step directions for making a full IC2 QuantumSuit? - li.intro Need help with that giant multi-block reactor from Big Reactors? - p.intro No problem. Crafting Guide can do it all. - p. - Configure which mods you're using, and the entire - site will update itself to your mod pack. - p. - Browse through your own customized item catalog to - see full recipe lists, related items, recipes added by each tool, and even which items can be - made from the item you're looking at. - p. - Craft any number of items from your mod pack to see a - full list of raw ingredients, and recipe-by-recipe instructions on how to make everything on - your list. No item is too complex, and no build is too big. - - .section - h2 What's new? - .panel - h3 2016-03-26 - .entry - p. - The second contribution comes from Jay Oliver who has - added the data files for Quantum Flux. Quantum Flux provides - various items for moving RF power wirelessly and manipulating the flow of time. It also - provides some pretty powerful powered armor. - p. - The third contribution, from ThePsionic, is a - BuildCraft add-on called Logistics Pipes. This mod adds - a whole complex set of pipes which allow automated retrieval, crafting, sorting, and more. - - h3 2016-03-25 - .entry - p. - I've gotten a few contributions of whole mods recently, and I'm catching up on getting them up - on the site. First up is Agricraft, contributed by - dragagon! Agricraft takes the idea of crops from IC2 - and pumps it up to a whole new level with a cross-breeding program that introduces a way to grow - anything from native Minecraft flowers all the way up to diamonds! - - h3 2016-02-11 - .entry - p. - I've been using Modular PowerSuits myself lately, and I - noticed that the newest version (finally!) comes with default recipes. So, I've updated - Crafting Guide to support both the newest vanilla recipes as well as those from Thermal - Expansion. You can switch back and forth on the Configure page. - - h3 2016-02-09 - .entry - p. - Back before the winter holidays, the extremely patient - tdallmann completed support for Hydraulicraft, and I'm - afraid I'm only now getting it up on the site! It looks like a neat mod based all around the - science of hydraulics with a nicely stepped set of devices to be made at each level. Many thanks - to tddallmann for adding it to Crafting Guide! - p. - I also received a submission for adding OpenComputers from - yut23. Should be a big help to those aspiring Minecraft - programmers who want a bit more challege than is provided by - ComputerCraft! Thanks, yut23! - - - h3 2015-11-25 - .entry - p. - With many thanks to Mike Caron, I'm pleased to announce - support for Storage Drawers! - - h3 2015-12-13 - .entry - p. - I'm super excited to announce that I've added full multi-block support for Crafting Guide! For - example, check out a 5-Core Reactor - from Big Reactors, or the 5x5x5 Steel Tank from - Railcraft. I'm really pleased with how it turned out! - - h3 2015-11-17 - .entry - p. - And today, it's Extra Cells! - - h3 2015-11-16 - .entry - p. - It's a small one, but also highly requested... Here's ComputerCraft! - - h3 2015-11-14 - .entry - p. - One more small one over the weekend... Advanced Solar - Panels has been added to crafting guide! - - h3 2015-11-14 - .entry - p. - For a long while now, Galacticraft has been the most - requested mod, and it's finally here! Enjoy! - - .panel - h3 2015-11-10 - .entry - p. - Remember me? They guy who runs the site. Yeah, I'm back, and with big news! The site now has - a completely new crafting algorithm. Instead of just taking the first crafting plan it comes up - with, it tries to compute every possible plan, rates them, and then picks the best one. This - also clears up a lot of bugs related to the old algorithm. The one drawback is that some items - can take a bit longer to compute than with the old way, but I think you'll find it's worth it! - p. - On a personal note, I think it's clear that I don't have nearly as much time to dedicate to the - site as I used to. That's mostly because I started a new job which keeps me away from working - on the site so much. I hope to be able to get into a more regular pace now things my personal - life has settled down again. - - h3 2015-07-25 - .entry - p. - You may have noticed things have been very quiet with the site for the past month... well I'm - afraid that's because I haven't been working on it. Instead, I've been hunting for a new job. - Now that I've got that all squared away (I'll be starting at Looker in Santa Cruz on Monday), - I'll have nights and weekends to continue working on the site. Thanks for being patient! - - h3 2015-06-12 - .entry - p. - Today I launched the second major part of the item description editor: image uploads! As you - enter your description, use the markdown notation for an image ![](image.png) and a - empty image preview will show up underneath the editor. Click the button to select an image from - your computer. Just be sure to keep the images to a reasonable size (< 750kB, and < 740px by - 600px). - - h3 2015-05-13 - .entry - p. - As of today, you can now add and edit item descriptions right on Crafting Guide. This feature is - starting small with just item descriptions, but eventually all the content on the site will be - editable. All you need is a (free) GitHub account, and you're ready to go! - p. - For those more comfortable with a regular text editor, all the content is still in GitHub under - the crafting-guide-data repo. - Just follow the instructions, and you can submit content via pull request instead of using the - website's editor. diff --git a/src/jade/templates/inventory.jade b/src/jade/templates/inventory.jade deleted file mode 100644 index a908902a0..000000000 --- a/src/jade/templates/inventory.jade +++ /dev/null @@ -1,13 +0,0 @@ -//- -//- Crafting Guide - inventory.jade -//- -//- Copyright (c) 2014-2015 by Redwood Labs -//- All rights reserved. -//- - -.view__inventory - .item_container - .empty_placeholder.hideable.hidden nothing - .buttons - .view__item_selector.hideable.hidden.button: p add an item... - .button.clear: p clear diff --git a/src/jade/templates/item.jade b/src/jade/templates/item.jade deleted file mode 100644 index f210ca3c3..000000000 --- a/src/jade/templates/item.jade +++ /dev/null @@ -1,13 +0,0 @@ -//- -//- Crafting Guide - item.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__item - a - table - tr - td.itemIcon: img - td.itemName(width="*") diff --git a/src/jade/templates/item_page.jade b/src/jade/templates/item_page.jade deleted file mode 100644 index 034be0812..000000000 --- a/src/jade/templates/item_page.jade +++ /dev/null @@ -1,42 +0,0 @@ -//- -//- Crafting Guide - item_page.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__item_page - .sidebar - .titleImage: a: img - a.officialPage.externalLink.hideable.hidden(target="new"): p Official Documentation - - button.large.craftingPlan See Crafting Plan - - ins.view__adsense - - .mainBody - h1.name - .byline.hideable.hidden: p from - - .recipes.section.hideable.hidden - h2 Recipes - .panel - - .multiblock.section.hideable.hidden - h2 Multiblock Construction - .panel - .view__multiblock_viewer - - .description.section - h2 Description - .panel.markdown - - .videos.section.hideable.hidden - h2 Videos - .panel - - .view__item_group.usedToMake - - .view__item_group.usedAsToolToMake - - .view__item_group.similar diff --git a/src/jade/templates/item_selector.jade b/src/jade/templates/item_selector.jade deleted file mode 100644 index 7fa9f1d6b..000000000 --- a/src/jade/templates/item_selector.jade +++ /dev/null @@ -1,12 +0,0 @@ -//- -//- Crafting Guide - item_selector.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__item_selector - .view__item_selector_popup.hideable.hiding - .search - input - .results \ No newline at end of file diff --git a/src/jade/templates/item_selector_element.jade b/src/jade/templates/item_selector_element.jade deleted file mode 100644 index 28f241f23..000000000 --- a/src/jade/templates/item_selector_element.jade +++ /dev/null @@ -1,11 +0,0 @@ -//- -//- Crafting Guide - item_selector_element.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__item_selector_element - img - .name: p - .modName: p diff --git a/src/jade/templates/login_page.jade b/src/jade/templates/login_page.jade deleted file mode 100644 index c96542532..000000000 --- a/src/jade/templates/login_page.jade +++ /dev/null @@ -1,64 +0,0 @@ -//- -//- Crafting Guide - login_page.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__login_page - .two-thirds-content.hideable.ready-to-login - img.float-right(src="/images/github-login-large.png") - h1 Login with GitHub - p. - Use your GitHub credentials to login and make changes on Crafting Guide. No GitHub account? Don't worry, you - can get one for free. read more... - .read-more-content.slideable.closed - p. - All changes you make on the site get submitted directly to our GitHub repo, and then published through - the same automated deployment process as changes made by anyone else. That way, anyone can contribute - easily: whether developer or end user. - p. - To log in, we redirect you to GitHub's site, and once you're signed in, they'll send you back here. We - never see your credentials, and only get the minimum set of permissions necessary to submit changes to - the Crafting Guide repo on your behalf. - p. - GitHub offers free accounts, so even if you don't already have one, you've got nothing to lose! - - .actions - button.huge Login with GitHub - - .clear - - .two-thirds-content.hideable.hidden.server-down - h1 Sorry! - p. - Our interactive editing service is down right now, but you can always submit a pull request over at - the Crafting Guide GitHub Repository. We'll have - the editing service back up soon! - - .two-thirds-content.hideable.hidden.invalid-callback - img.float-right(src="/images/github-login-large.png") - h1 Oops! - p. - Sorry about that, but it looks like something went wrong with your GitHub login. Click the button below to - try again, or use the Feedback button on the left to let us know, and we'll try to help. - - .actions - button.huge Login with GitHub - - .clear - - .two-thirds-content.hideable.hidden.fetching-token - img.float-right(src="/images/github-login-large.png") - h1 Completing log in... - p Hang on just a second while we finish logging you in... - .actions - img(src="/images/wait.gif") - - .clear - - .two-thirds-content.hideable.hidden.logged-in - img.float-right(src="/images/github-login-large.png") - h1 All set! - - .clear diff --git a/src/jade/templates/markdown_section.jade b/src/jade/templates/markdown_section.jade deleted file mode 100644 index 02607f4f3..000000000 --- a/src/jade/templates/markdown_section.jade +++ /dev/null @@ -1,37 +0,0 @@ -//- -//- Crafting Guide - markdown_section.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__markdown_section.section - h2 - .panel - .waiting: img(src='/images/wait.gif') - .markdown - .creating - p Please help by adding a description! - .editor - .instructions - p. - Edit using GitHub - Flavored Markdown. Use [[Item Name]] to link to another item and - ![](image.png) to add an image. - textarea - .sizer - .image_list - .buttons - .error: p - .question: a(href="javascript:void;") Confused? Click here to ask a question! - button.return return - button.cancel cancel - button.preview preview - button.save save - button.edit edit - .confirming - p Thanks for your help! - p Your changes will appear on the site in a few minutes. - .appologizing - p Sorry, but something went wrong. - p Please try again after a few moments. \ No newline at end of file diff --git a/src/jade/templates/mod.jade b/src/jade/templates/mod.jade deleted file mode 100644 index 0252c1258..000000000 --- a/src/jade/templates/mod.jade +++ /dev/null @@ -1,14 +0,0 @@ -//- -//- Crafting Guide - mod.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__mod - a - .left - img.logo - .right - h3.name: p - .description: p diff --git a/src/jade/templates/mod_pack.jade b/src/jade/templates/mod_pack.jade deleted file mode 100644 index d20504f93..000000000 --- a/src/jade/templates/mod_pack.jade +++ /dev/null @@ -1,16 +0,0 @@ -//- -//- Crafting Guide - mod_pack.jade -//- -//- Copyright (c) 2014-2015 by Redwood Labs -//- All rights reserved. -//- - -.view__mod_pack - h2 - img(src="/images/bookshelf.png") - p Mod Pack - - .panel - .mods - .toolbar - button(name="suggestMod") suggest a mod \ No newline at end of file diff --git a/src/jade/templates/mod_page.jade b/src/jade/templates/mod_page.jade deleted file mode 100644 index 2af6057cf..000000000 --- a/src/jade/templates/mod_page.jade +++ /dev/null @@ -1,27 +0,0 @@ -//- -//- Crafting Guide - mod_page.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__mod_page - .sidebar - .titleImage: a: img - select.version - a.homePage.externalLink.hideable.hidden(target="new"): p Offical Home Page - a.documentation.externalLink.hideable.hidden(target="new"): p Documentation - a.download.externalLink.hideable.hidden(target="new"): p Download - - .view__adsense - - .mainBody - h1.name - .byline: p - .description: p - - .tutorials.section.hideable.hidden - h2 Tutorials - .panel - - .itemGroups diff --git a/src/jade/templates/mod_selector.jade b/src/jade/templates/mod_selector.jade deleted file mode 100644 index 8169f3e56..000000000 --- a/src/jade/templates/mod_selector.jade +++ /dev/null @@ -1,14 +0,0 @@ -//- -//- Crafting Guide - mod_selector.jade -//- -//- Copyright (c) 2014-2015 by Redwood Labs -//- All rights reserved. -//- - -.view__mod_selector - .version - select - option(value="none") None - .name - a: p - .description: p diff --git a/src/jade/templates/stack.jade b/src/jade/templates/stack.jade deleted file mode 100644 index 3c8b64020..000000000 --- a/src/jade/templates/stack.jade +++ /dev/null @@ -1,14 +0,0 @@ -//- -//- Crafting Guide - stack.jade -//- -//- Copyright (c) 2014-2015 by Redwood Labs -//- All rights reserved. -//- - -.view__stack - .quantity: .bubble: input - .icon: img(src='') - .name: a - .action - button.second   - button.first   diff --git a/src/jade/templates/step.jade b/src/jade/templates/step.jade deleted file mode 100644 index f95647deb..000000000 --- a/src/jade/templates/step.jade +++ /dev/null @@ -1,15 +0,0 @@ -//- -//- Crafting Guide - step.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__step - h3 - .main_content - .view__inventory - .view__minimal_recipe - .buttons - .button.complete: p complete step - .button.tool: p also make this tool diff --git a/src/jade/templates/tutorial_page.jade b/src/jade/templates/tutorial_page.jade deleted file mode 100644 index 081a16fa0..000000000 --- a/src/jade/templates/tutorial_page.jade +++ /dev/null @@ -1,23 +0,0 @@ -//- -//- Crafting Guide - tutorial_page.jade -//- -//- Copyright (c) 2015 by Redwood Labs -//- All rights reserved. -//- - -.view__tutorial_page - .sidebar - .titleImage: a: img - a.officialPage.externalLink.hideable.hidden(target="new"): p Offical Documentation - - ins.view__adsense - - .mainBody - h1.name - .byline: p from - - .sections - - .videos.section.hideable.hidden - h2 - .panel diff --git a/src/scss/addthis.scss b/src/scss/addthis.scss deleted file mode 100644 index 25b9b5959..000000000 --- a/src/scss/addthis.scss +++ /dev/null @@ -1,14 +0,0 @@ -/* -Crafting Guide - addthis.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.addthis_sharing_toolbox { - position: absolute; top: 0.65em; right: 0.65em; - - div { - text-align: right; - } -} diff --git a/src/scss/classes.scss b/src/scss/classes.scss deleted file mode 100644 index 605ee0704..000000000 --- a/src/scss/classes.scss +++ /dev/null @@ -1,203 +0,0 @@ -/* -Crafting Guide - classes.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.button { - background: $color-gray-faint; - border: 0.1em solid $color-gray-medium; - border-radius: 1.5em; - cursor: pointer; - padding: 0.5em 0.75em; - margin: 0 1em; - - &:hover { - background: $color-background-panel; - } - - &.disabled { - background: $color-background-panel; - border: 0.1em solid $color-gray-light; - cursor: inherit; - - p { - color: $color-gray-light; - } - } - - p { - color: $color-active; - font-family: $font-family-normal; - font-weight: bold; - text-align: center; - } -} - -.byline { - margin: 0.25em 0 2em 0; - - p { - font-family: $font-family-normal; - font-size: $font-size-normal; - font-style: italic; - } -} - -.centered { - text-align: center; -} - -.clear { - clear: both; -} - -body > .content { - background: $color-content; - box-shadow: 10px 10px 20px #666; - margin: 2em auto; - max-width: 96em; - position: relative; - width: 100%; -} - -.error { background: $color-error; } - -.error-new { background: $color-error-new; } - -.float-right { - float: right; - margin-left: 3em; -} - -.hideable { - opacity: 1; - transition: opacity $animate-normal; -} - -.hiding { - opacity: 0; -} - -.hidden { - opacity: 0; - display: none; -} - -.mainBody { - position: relative; width: 81.25%; - - display: inline-block; - padding: 1em; - padding-top: 2em; - vertical-align: top; -} - -.page { - overflow: hidden; -} - -.page-loading { - width: 100%; - - text-align: center; - - img { - margin: 5em auto; - } -} - -.sidebar { - position: relative; width: 18.75%; height: 100%; - - display: inline-block; - padding: 1em; - vertical-align: top; - - .titleImage { - margin-bottom: 2em; - - a { - img { - position: relative; width: 16em; min-height: 16em; - @include pixel-image; - } - } - } - - .externalLink { - position: relative; width: 80%; - margin: 0.5em 10%; - - p { - font-family: $font-family-normal; - font-size: $font-size-normal; - text-align: center; - } - } -} - -.section { - margin-top: 3em; - - h2 { - font-family: $font-family-header; - font-size: $font-size-large; - margin-bottom: 0.5em; - - &:first-child { - margin-top: 0; - } - } - - h3 { - font-family: $font-family-header; - font-size: $font-size-normal; - margin: 2em 0 0 0.5em; - - &:first-child { - margin-top: 0; - } - } - - .entry { - position: relative; width: 100%; - padding: 0 2em; - } - - .panel { - background: white; - padding: 1em; - } - - &:first-child { - margin-top: 0; - } -} - -.slideable { - max-height: 500px; - overflow: hidden; - transition: max-height $animate-normal; - - &.closed { - max-height: 0; - } -} - -.stop-scrolling { - height: 100%; - overflow: hidden; -} - -.two-thirds-content { - position: relative; width: 66%; - margin: 5em 16.5%; -} - -.videos { - .panel { - text-align: center; - } -} \ No newline at end of file diff --git a/src/scss/main.scss b/src/scss/main.scss deleted file mode 100644 index a9c322a6f..000000000 --- a/src/scss/main.scss +++ /dev/null @@ -1,103 +0,0 @@ -/* -Crafting Guide - main.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -@import 'mixins'; -@import 'reset'; - -// Fonts /////////////////////////////////////////////////////////////////////////////////////////////////////////////// - -@font-face { - font-family: 'PressStart'; - font-style: normal; - font-weight: 400; - src: url('/fonts/press_start.ttf') format('truetype'); -} - -@font-face { - font-family: 'Silkscreen'; - font-style: normal; - font-weight: 400; - src: url('/fonts/silkscreen.ttf') format('truetype'); -} - -// Constants /////////////////////////////////////////////////////////////////////////////////////////////////////////// - -// Animation Speeds //////////////////////////////////////////////////////////////////////////////// - -$animate-fast: 0.200s; -$animate-normal: 0.400s; -$animate-slow: 1.200s; - -// Font Faces ////////////////////////////////////////////////////////////////////////////////////// - -$font-family-header: 'Silkscreen'; -$font-family-normal: sans-serif; -$font-family-input: monospace; - -// Font Sizes ////////////////////////////////////////////////////////////////////////////////////// - -$font-size-small: 1.25em; -$font-size-normal: 1.5em; -$font-size-large: 2.0em; -$font-size-x-large: 3.0em; -$font-size-xx-large: 4.0em; - -// Gray Palette //////////////////////////////////////////////////////////////////////////////////// - -$color-gray-faint: #F2F2F2; -$color-gray-light: #CCCCCC; -$color-gray-medium: #A6A6A6; -$color-gray-dark: #8B8B8B; -$color-gray-shadow: #444444; - -// Object Background Colors //////////////////////////////////////////////////////////////////////// - -$color-bedrock: #0A0A0A; -$color-brick-dark: #7A7A7A; -$color-brick-light: #D9D9D9; -$color-dirt: #906647; -$color-ice: #8AA7E6; - -// Opacity Values ////////////////////////////////////////////////////////////////////////////////// - -$opacity-hidden: 0.000001; -$opacity-shown: 1.0; - -// Style Colors //////////////////////////////////////////////////////////////////////////////////// - -$color-active: #5C8AE6; -$color-active-hover: #2E6BE6; -$color-background: #AAC9FF; -$color-background-panel: #FFFFFF; -$color-background-toolbar: rgba(255, 255, 255, 0.75); -$color-checkmark: #7EDD7B; -$color-content: rgba(230, 230, 230, 0.90); -$color-error: #F3C2C2; -$color-error-new: #CD0000; -$color-footer: #3D1D09; -$color-footer-text: #FFFFFF; -$color-link: #0000FF; -$color-link-subtle: #545A99; -$color-text: #000000; -$color-text-light: #FFFFFF; -$color-white: #FFFFFF; - -// Z-Index Layers ////////////////////////////////////////////////////////////////////////////////// - -$layer-normal: 100; -$layer-screen: 1000; -$layer-dialog: 10000; - -// Child Stylesheets /////////////////////////////////////////////////////////////////////////////////////////////////// - -@import 'classes'; -@import 'markdown'; -@import 'tags'; -@import 'views'; - -@import 'templates/index'; -@import 'addthis'; \ No newline at end of file diff --git a/src/scss/markdown.scss b/src/scss/markdown.scss deleted file mode 100644 index 11fb99e2e..000000000 --- a/src/scss/markdown.scss +++ /dev/null @@ -1,95 +0,0 @@ -/* -Crafting Guide - markdown.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.markdown { - - a { - color: $color-link-subtle; - text-decoration: none; - - &:hover { - color: $color-link; - text-decoration: underline; - } - } - - h1 { - font-family: $font-family-normal; - font-size: $font-size-large; - font-weight: bold; - margin: 1.5em 0 0.25em 0; - } - - img { - max-width: 100%; - } - - p { - font-family: $font-family-normal; - font-size: $font-size-normal; - line-height: $font-size-normal + 0.15em; - margin-top: 1.33em; - } - - table { - margin: 2em auto 0 auto; - - td { - font-family: $font-family-normal; - font-size: $font-size-normal; - padding: 0.1em 1em; - vertical-align: middle; - } - - th { - font-family: $font-family-normal; - font-size: $font-size-normal; - font-weight: bold; - padding: 0.1em 1em; - vertical-align: middle; - text-align: center; - } - - td[align="center"] { - text-align: center; - } - td[align="right"] { - text-align: right; - } - } - - ol { - margin: 2em 2em 0 2em; - - li { - font-family: $font-family-normal; - font-size: $font-size-normal; - line-height: $font-size-normal + 0.15em; - list-style: decimal; - margin: 0.66em 0 0 2em; - } - } - - - ul { - margin: 2em 2em 0 2em; - - li { - font-family: $font-family-normal; - font-size: $font-size-normal; - line-height: $font-size-normal + 0.15em; - list-style: disc; - margin: 0.66em 0 0 2em; - } - } - - & > * { - &:first-child { - margin-top: 0; - } - } -} diff --git a/src/scss/mixins.scss b/src/scss/mixins.scss deleted file mode 100644 index d05ba268b..000000000 --- a/src/scss/mixins.scss +++ /dev/null @@ -1,34 +0,0 @@ -/* -Crafting Guide - mixins.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -@mixin box-sizing($value) { - -moz-box-sizing: $value; - -webkit-box-sizing: $value; - box-sizing: $value; -} - -@mixin center-vertical { - position: absolute; - top: 50%; - @include transform(translateY(-50%)); -} - -@mixin transform($transforms) { - -moz-transform: $transforms; - -o-transform: $transforms; - -ms-transform: $transforms; - -webkit-transform: $transforms; - transform: $transforms; -} - -@mixin pixel-image { - image-rendering: -moz-crisp-edges; /* Firefox */ - image-rendering: -o-crisp-edges; /* Opera */ - image-rendering: -webkit-optimize-contrast; /* Webkit (non-standard naming) */ - image-rendering: crisp-edges; - -ms-interpolation-mode: nearest-neighbor; /* IE (non-standard property) */ -} diff --git a/src/scss/reset.scss b/src/scss/reset.scss deleted file mode 100644 index ea6465056..000000000 --- a/src/scss/reset.scss +++ /dev/null @@ -1,76 +0,0 @@ -a,abbr,acronym,address,applet,article,aside,audio,b,big,blockquote,body,canvas,caption,center,cite,code,dd,del,details,dfn,dialog,div,dl,dt,em,embed,fieldset,figcaption,figure,font,footer,form,h1,h2,h3,h4,h5,h6,header,hgroup,hr,html,i,iframe,img,ins,kbd,label,legend,li,mark,menu,meter,nav,object,ol,output,p,pre,progress,q,rp,rt,ruby,s,samp,section,small,span,strike,strong,sub,summary,sup,table,tbody,td,textarea,tfoot,th,thead,time,td,tr,tt,u,ul,var,video,xmp { - border: 0; - margin: 0; - padding: 0; - font-size: 100%; - @include box-sizing(border-box); -} - -html,body { - height: 100%; -} - -article,aside,details,figcaption,figure,footer,header,hgroup,menu,nav,section { - display: block; -} - -b,strong { - font-weight: bold; -} - -img { - color: transparent; - vertical-align: middle; - -ms-interpolation-mode: bicubic; -} - -ol,ul { - list-style: none; -} - -li { - display: list-item; -} - -table { - border-collapse: collapse; - border-spacing: 0; -} - -th,td,caption { - font-weight: normal; - vertical-align: top; - text-align: left; - @include box-sizing(border-box); -} - -q { - quotes: none; -} - -q:before,q:after { - content: ''; - content: none; -} - -sub,sup,small { - font-size: 75%; -} - -sub,sup { - line-height: 0; - position: relative; - vertical-align: baseline; -} - -sub { - bottom: -0.25em; -} - -sup { - top: -0.5em; -} - -svg { - overflow: hidden; -} \ No newline at end of file diff --git a/src/scss/tags.scss b/src/scss/tags.scss deleted file mode 100644 index b84a7b563..000000000 --- a/src/scss/tags.scss +++ /dev/null @@ -1,117 +0,0 @@ -/* -Crafting Guide - tags.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -body { - background: $color-background url('/images/ice.png'); - font-size: 10px; -} - -button { - background: $color-gray-faint; - border: 0.1em solid $color-gray-medium; - border-radius: 1em; - color: $color-active; - cursor: pointer; - font-size: $font-size-normal; - font-weight: bold; - outline: none; - padding: 0.1em 1em; - - &:active { - background: $color-active; - color: $color-white; - } - - &:hover { - background: $color-white; - color: $color-active-hover; - } - - &:disabled { - background: $color-white !important; - color: $color-gray-light !important; - cursor: default !important; - } - - &.large { - margin: 2em 0; - padding: 0.5em 0.5em; - } - - &.huge { - font-size: $font-size-large; - padding: 0.5em 3em; - } -} - -h1 { - margin-bottom: 1em; - - & > * { - display: inline-block; - vertical-align: middle; - } - - img { - height: 6.4em; width: 6.4em; - margin-right: 1em; - } - - p { - font-family: $font-family-header; - font-size: $font-size-xx-large; - } - - &.name { - font-family: $font-family-header; - font-size: $font-size-x-large; - margin: 0; - } -} - -h2 { - margin-bottom: 0.5em; - - & > * { - display: inline-block; - vertical-align: middle; - } - - img { - height: 3.2em; width: 3.2em; - margin-right: 1em; - } - - p { - font-family: $font-family-header; - font-size: $font-size-x-large; - } -} - -h3 { - margin-bottom: 0.5em; - - p { - font-family: $font-family-header; - font-size: $font-size-normal; - } -} - -p { - font-family: $font-family-normal; - font-size: $font-size-normal; -} - -input { - font-family: $font-family-input; - font-size: $font-size-normal; -} - -label { - font-family: $font-family-normal; - font-size: $font-size-normal; -} \ No newline at end of file diff --git a/src/scss/templates/adsense.scss b/src/scss/templates/adsense.scss deleted file mode 100644 index f89ba8ccf..000000000 --- a/src/scss/templates/adsense.scss +++ /dev/null @@ -1,19 +0,0 @@ -/* -Crafting Guide - adsense.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__adsense { - - .sidebar_skyscraper { - position: relative; width: 160px; height: 600px; - border: 0.1em solid $color-gray-faint; - margin: 3em 0; - - &:first-child { - margin-top: 0; - } - } -} diff --git a/src/scss/templates/browse_page.scss b/src/scss/templates/browse_page.scss deleted file mode 100644 index 7e0820706..000000000 --- a/src/scss/templates/browse_page.scss +++ /dev/null @@ -1,22 +0,0 @@ -/* -Crafting Guide - browse_page.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__browse_page { - .mods { - display: flex; - flex-wrap: wrap; - align-items: stretch; - - .view__mod { - flex: 1 1 100%; - flex-wrap: nowrap; - - margin: 0 1em 1em 0; - max-width: calc(50% - 1em); - } - } -} diff --git a/src/scss/templates/craft_page.scss b/src/scss/templates/craft_page.scss deleted file mode 100644 index ac2464b3f..000000000 --- a/src/scss/templates/craft_page.scss +++ /dev/null @@ -1,50 +0,0 @@ -/* -Crafting Guide - craft_page.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -.view__craft_page { - - .want.section { - .view__inventory { - position: relative; width: 100%; - } - } - - .tools.section { - .options { - margin-top: 4em; - } - } - - .ingredients.section { - .need { - margin-top: 4em; - } - } - - .instructions.section { - p { - font-size: $font-size-large; - margin-top: 1em; - - &:first-child { - margin-top: 0; - } - } - - ol { - margin: 2em 3em 0 3em; - - li { - font-family: $font-family-normal; - font-size: $font-size-large; - line-height: $font-size-normal + 0.15em; - list-style: decimal; - margin: 0.66em 0 0 2em; - } - } - } -} diff --git a/src/scss/templates/crafting_grid.scss b/src/scss/templates/crafting_grid.scss deleted file mode 100644 index a1889e841..000000000 --- a/src/scss/templates/crafting_grid.scss +++ /dev/null @@ -1,21 +0,0 @@ -/* -Crafting Table - crafting_grid.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -.view__crafting_grid { - border: 0.2em solid $color-gray-medium; - - img { - position: relative; height:4.8em; width: 4.8em; - } - - td { - height: 4.8em; width: 4.8em; - background: $color-gray-faint; - border: 0.1em solid $color-gray-light; - padding: 0.1em; - } -} diff --git a/src/scss/templates/crafting_table.scss b/src/scss/templates/crafting_table.scss deleted file mode 100644 index 73de2431f..000000000 --- a/src/scss/templates/crafting_table.scss +++ /dev/null @@ -1,62 +0,0 @@ -/* -Crafting Table - crafting_table.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -.view__crafting_table { - min-height: 14em; - width: 100%; - - .panel { - position: absolute; top: 3.6em; right: 2em; bottom: 0; left: 2em; - background: $color-background-panel; - - .next { - background: url('/images/arrow-right-disabled.png'); - position: absolute; top: 50%; right: 1em; height: 8em; width: 4em; - @include transform(translateY(-50%)); - - &.enabled { - background: url('/images/arrow-right.png'); - cursor: pointer; - - &:hover { background: url('/images/arrow-right-hover.png'); } - } - } - - .view__minimal_recipe { - position: absolute; top: 50%; left: 50%; - @include transform(translate(-50%, -50%)); - } - - .prev { - background: url('/images/arrow-left-disabled.png'); - position: absolute; top: 50%; left: 1em; height: 8em; width: 4em; - @include transform(translateY(-50%)); - - &.enabled { - background: url('/images/arrow-left.png'); - cursor: pointer; - - &:hover { background: url('/images/arrow-left-hover.png'); } - } - } - - .problem { - position: absolute; bottom: 1em; right: 1em; - - a { - color: $color-gray-light; - cursor: pointer; - font-size: $font-size-normal; - text-decoration: underline; - - &:hover { - color: $color-gray-medium; - } - } - } - } -} diff --git a/src/scss/templates/craftsman_working.scss b/src/scss/templates/craftsman_working.scss deleted file mode 100644 index 57ede871a..000000000 --- a/src/scss/templates/craftsman_working.scss +++ /dev/null @@ -1,35 +0,0 @@ -/* -Crafting Table - crafting_table.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -.view__craftsman_working .content { - align-items: center; - background: $color-white; - box-shadow: none; - display: flex; - flex-direction: column; - padding: 3em; - - .waiting { - margin-bottom: 3em; - } - - .message { - margin-bottom: 1em; - - p { - font-family: $font-family-header; - font-size: $font-size-large; - } - } - - .count { - p { - font-family: $font-family-header; - font-size: $font-size-normal; - } - } -} \ No newline at end of file diff --git a/src/scss/templates/feedback.scss b/src/scss/templates/feedback.scss deleted file mode 100644 index 21f5dbf38..000000000 --- a/src/scss/templates/feedback.scss +++ /dev/null @@ -1,84 +0,0 @@ -/* -Crafting Guide - feedback.scss - -Copyright (c) 2014 by Redwood Labs -All rights reserved. -*/ - -.view__feedback { - position: fixed; top: 50%; left: -30em; width: 25em; - @include transform(translateY(-50%)); - - background: white; - border: 0.2em solid $color-gray-dark; - border-left: 0; - border-right: 0.1em solid $color-gray-faint; - box-size: border-box; - box-shadow: 0.3em 0.3em 0.6em 0 $color-gray-shadow; - padding: 2em; - z-index: $layer-dialog; - - .error { - background: white; - clear: both; - display: none; - margin-top: 4em; - text-align: center; - - p { - color: $color-error-new; - font-family: $font-family-normal; - font-size: $font-size-small; - } - } - - .label { - position: absolute; top: -0.2em; right: -4.5em; bottom:-0.2em; width: 4.5em; - - background: $color-gray-faint; - border: 0.2em solid $color-gray-dark; - border-bottom-right-radius: 1.0em; - border-left: 0; - border-top-right-radius: 1.0em; - box-shadow: 0.3em 0.3em 0.6em 0 $color-gray-shadow; - cursor: pointer; - text-align: center; - z-index: $layer-dialog - 1; - - img { - position: absolute; top: 0.5em; left: 50%; height: 3.6em; width: 3.6em; - @include transform(translateX(-50%)); - } - - p { - position: absolute; top: 50%; left: 50%; - @include transform(translateX(-50%) rotate(-90deg)); - - font-family: $font-family-header; - font-size: $font-size-x-large; - } - } - - button[name="send"] { - float: right; - margin-top: 0.5em; - } - - input { - position: relative; width: 100%; - - border: 1px solid $color-gray-light; - box-sizing: border-box; - margin-bottom: 1em; - padding: 0.2em; - } - - textarea { - border: 1px solid $color-gray-light; - position: relative; height: 11.5em; width: 100%; - - font-family: $font-family-input; - font-size: $font-size-normal; - resize: vertical; - } -} diff --git a/src/scss/templates/full_recipe.scss b/src/scss/templates/full_recipe.scss deleted file mode 100644 index e6b3911de..000000000 --- a/src/scss/templates/full_recipe.scss +++ /dev/null @@ -1,57 +0,0 @@ -/* -Crafting Table - full_recipe.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -.view__full_recipe { - display: block; - - & > div { - position: relative; width: 33%; - display: inline-block; - vertical-align: top; - } - - .pattern { - .view__crafting_grid { - position: relative; left: 50%; - @include transform(translateX(-50%)); - } - - .tool { - margin-top: 0.5em; - text-align: center; - - p { - font-weight: bold; - } - } - } - - .input { - .view__inventory { - width: 100%; - } - } - - .tool { - a { - color: $color-text; - font-family: $font-family-normal; - font-size: $font-size-normal; - font-weight: bold; - text-decoration: none; - - &:hover { - color: $color-link; - text-decoration: underline; - } - } - } - - h3 { - margin-top: 0; margin-left: 0; - } -} diff --git a/src/scss/templates/home_page.scss b/src/scss/templates/home_page.scss deleted file mode 100644 index eeca3324c..000000000 --- a/src/scss/templates/home_page.scss +++ /dev/null @@ -1,56 +0,0 @@ -/* -Crafting Guide - home_page.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__home_page { - h2 { - font-size: $font-size-x-large; - } - - p { - font-family: $font-family-normal; - font-size: $font-size-normal; - line-height: 1.25em; - margin: 1em 0; - - &:first-child { - margin-top: 0; - } - - &:last-child { - margin-bottom: 0; - } - } - - li { - font-family: $font-family-normal; - font-size: $font-size-normal; - margin-bottom: 0.5em; - } - - ol { - list-style-type: decimal; - margin: 0.5em 4em 2em 4em; - } - - ul { - list-style: disc outside; - margin: 0.5em 4em 2em 4em; - } - - .intro { - font-size: $font-size-large; - } - - .section:first-child { - margin-top: 0; - } - - .section-link { - color: $color-active; - font-weight: bold; - } -} diff --git a/src/scss/templates/index.scss b/src/scss/templates/index.scss deleted file mode 100644 index a17bde05f..000000000 --- a/src/scss/templates/index.scss +++ /dev/null @@ -1,37 +0,0 @@ -/* -Crafting Guide - templates/index.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -@import 'adsense'; -@import 'browse_page'; -@import 'crafting_grid'; -@import 'crafting_table'; -@import 'craft_page'; -@import 'craftsman_working'; -@import 'feedback'; -@import 'full_recipe'; -@import 'home_page'; -@import 'inventory'; -@import 'item'; -@import 'item_page'; -@import 'item_selector'; -@import 'item_selector_element'; -@import 'login_page'; -@import 'markdown_image'; -@import 'markdown_image_list'; -@import 'markdown_section'; -@import 'multiblock'; -@import 'multiblock_viewer'; -@import 'minimal_recipe'; -@import 'mod'; -@import 'mod_pack'; -@import 'mod_page'; -@import 'mod_selector'; -@import 'slot'; -@import 'stack'; -@import 'step'; -@import 'tutorial'; -@import 'video'; diff --git a/src/scss/templates/inventory.scss b/src/scss/templates/inventory.scss deleted file mode 100644 index 04defe8a2..000000000 --- a/src/scss/templates/inventory.scss +++ /dev/null @@ -1,47 +0,0 @@ -/* -Crafting Guide - inventory.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -.view__inventory { - display: flex; - flex-direction: column; - - &.large { - .item_container { - font-size: 1.5em; - font-weight: bold; - } - } - - .empty_placeholder { - color: $color-gray-light; - font-family: $font-family-normal; - font-size: $font-size-large; - margin: 2em 0; - text-align: center; - } - - .item_container { - display: flex; - flex-direction: column; - } - - .buttons { - display: flex; - flex-direction: row; - - margin: 1em 2em; - - .view__item_selector { - flex: 85%; - margin-right: 1em; - } - - .button.clear { - flex: 15%; - } - } -} diff --git a/src/scss/templates/item.scss b/src/scss/templates/item.scss deleted file mode 100644 index 6a7202154..000000000 --- a/src/scss/templates/item.scss +++ /dev/null @@ -1,49 +0,0 @@ -/* -Crafting Guide - item.scss - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__item { - display: inline-block; - padding: 0.5em; - - a { - text-decoration: none; - width: 100%; - - &:hover { - .itemName { - color: $color-link; - text-decoration: underline; - } - - table { - background: $color-gray-faint; - } - } - } - - table { - width: 100%; - } - - td.itemName { - color: $color-text; - font-family: $font-family-normal; - font-size: $font-size-normal; - font-weight: bold; - padding-left: 1em; - text-align: left; - vertical-align: middle; - } - - td.itemIcon { - width: 3.6em; - - img { - height: 3.6em; width: 3.6em; - } - } -} diff --git a/src/scss/templates/item_page.scss b/src/scss/templates/item_page.scss deleted file mode 100644 index 77ab406b3..000000000 --- a/src/scss/templates/item_page.scss +++ /dev/null @@ -1,36 +0,0 @@ -/* -Crafting Guide - item_page.scss - -Copyright (c) 2014 by Redwood Labs -All rights reserved. -*/ - -.view__item_page { - & > div { - vertical-align: top; - display: inline-block; - } - - .sidebar { - button.large { - width: 100%; - } - } - - .mainBody { - .recipes { - .view__full_recipe { - width: 100%; - margin-top: 3em; - - &:first-child { - margin-top: 0; - } - } - } - } - - .view__item { - position: relative; width: 33%; - } -} diff --git a/src/scss/templates/item_selector.scss b/src/scss/templates/item_selector.scss deleted file mode 100644 index 00082ff10..000000000 --- a/src/scss/templates/item_selector.scss +++ /dev/null @@ -1,58 +0,0 @@ -/* -Crafting Guide - item_selector.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__item_selector { - position: relative; min-height: $font-size-normal * 2; min-width: 20em; - - border: 0.1em solid $color-gray-medium; - border-radius: 1.5em; - cursor: pointer; - padding: 0 0.75em; - - &.search { - background: $color-background-panel; - - p { - color: $color-gray-medium; - font-family: $font-family-input; - } - } - - p { - position: absolute; top: 50%; width: 100%; - @include transform(translateY(-50%)); - font-size: $font-size-normal; - } -} - -.view__item_selector_popup { - position: absolute; top: 0; left: 0; - min-height: 5em; - - background: $color-background-panel; - border: 0.1em solid $color-gray-medium; - border-radius: 1.5em 1.5em 0 0; - box-shadow: 10px 10px 20px #666; - - .search { - border-bottom: 0.1em solid $color-gray-medium; - margin: 1em; - - input { - border: none; - outline: none; - width: 100%; - } - } - - .results { - position: relative; - max-height: 50em; - overflow-y: auto; - padding-bottom: 1em; - } -} diff --git a/src/scss/templates/item_selector_element.scss b/src/scss/templates/item_selector_element.scss deleted file mode 100644 index 0320455e9..000000000 --- a/src/scss/templates/item_selector_element.scss +++ /dev/null @@ -1,31 +0,0 @@ -/* -Crafting Guide - item_selector_element.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__item_selector_element { - height: 4.0em; - padding: 0.2em 1em; - clear: both; - - transition: background $animate-fast, color $animate-fast; - - &.selected { - background: $color-active-hover; - color: $color-text-light; - } - - img { - height: 3.6em; width: 3.6em; - float: left; - margin-right: 1em; - } - - .modName p { - color: $color-gray-medium; - font-size: $font-size-small; - margin-top: 0.2em; - } -} diff --git a/src/scss/templates/login_page.scss b/src/scss/templates/login_page.scss deleted file mode 100644 index 9ce13fcd3..000000000 --- a/src/scss/templates/login_page.scss +++ /dev/null @@ -1,33 +0,0 @@ -/* -Crafting Guide - login_page.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__login_page { - - button { - outline: none; - } - - h1 { - font-family: $font-family-header; - font-size: $font-size-x-large; - padding-top: 2em; - } - - p { - margin-bottom: 1em; - } - - .actions { - margin-top: 4em; - width: 100%; - text-align: center; - } - - .read-more { - font-size: 75%; - } -} diff --git a/src/scss/templates/markdown_image.scss b/src/scss/templates/markdown_image.scss deleted file mode 100644 index dd184cb80..000000000 --- a/src/scss/templates/markdown_image.scss +++ /dev/null @@ -1,61 +0,0 @@ -/* -Crafting Guide - markdown_image.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__markdown_image { - position: relative; min-width: 33em; - - display: inline-block; - margin: 0 2em 1em 0; - overflow: hidden; - vertical-align: top; - - .thumbnail { - position: absolute; height: 10em; width: 10em; - - background: $color-gray-faint; - border: 0.1em solid $color-gray-light; - border-radius: 1em; - - img { - position: absolute; top: 50%; left: 50%; - @include transform(translate(-50%, -50%)); - max-width: 90%; max-height: 90%; - } - } - - .dynamic { - min-height: 7.5em; min-width: 22em; - margin: 0 0 3.5em 11em; - - .fileName { - min-height: 2em; - - p { - font-weight: bold; - } - } - } - - button { - position: absolute; left: 7.33em; bottom: 0.66em; - } - - input { - position: absolute; top: -5em; - } - - .loading { - height: 10em; width: 33em; - - p { - position: absolute; top: 50%; left: 50%; - @include transform(translate(-50%, -50%)); - - color: $color-gray-light; - } - } -} \ No newline at end of file diff --git a/src/scss/templates/markdown_image_list.scss b/src/scss/templates/markdown_image_list.scss deleted file mode 100644 index 7edae70da..000000000 --- a/src/scss/templates/markdown_image_list.scss +++ /dev/null @@ -1,18 +0,0 @@ -/* -Crafting Guide - markdown_image_list.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__markdown_image_list { - position: relative; min-width: 33em; width: 100%; - - border-bottom: 0.1em solid $color-gray-medium; - margin: 2em 0; - padding: 0 0 2em 0; - - h3 { - margin-bottom: 1em; - } -} diff --git a/src/scss/templates/markdown_section.scss b/src/scss/templates/markdown_section.scss deleted file mode 100644 index c944fcb1c..000000000 --- a/src/scss/templates/markdown_section.scss +++ /dev/null @@ -1,128 +0,0 @@ -/* -Crafting Guide - markdown_section.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__markdown_section { - - .appologizing, .confirming { - width: 100%; - - p { - width: 100%; - - margin: 1em auto; - text-align: center; - - &:first-child { - font-size: $font-size-x-large; - margin-top: 2em; - } - - &:last-child { - margin-bottom: 4em; - } - } - } - - .buttons { - position: relative; width: 100%; - - text-align: right; - - button { - margin: 0.66em 0 0 0.66em; - min-width: 6.66em; - padding: 0.25em 0.5em; - } - - .error { - - height: 100%; - - background: none; - display: inline-block; - - p { - color: $color-error-new; - font-weight: bold; - } - } - - .question { - position: absolute; top: 50%; left: 1em; - - a { - color: $color-gray-medium; - font-family: $font-family-normal; - font-size: $font-size-small; - font-style: italic; - text-decoration: underline; - } - } - } - - .creating { - width: 100%; - text-align: center; - - p { - color: $color-gray-light; - font-size: $font-size-x-large; - margin: 1em; - } - } - - .editor { - width: 100%; - - position: relative; - min-height: 11.5em; - - textarea, .sizer { - width: 100%; - border: 1px solid $color-gray-light; - font-family: $font-family-input; - font-size: $font-size-normal; - } - - textarea { - position: absolute; height: calc(100% - 1.5em); width: 100%; - - background: $color-gray-faint; - resize: none; - z-index: $layer-normal; - - &:focus { - background: $color-background-panel; - border: 1px solid $color-gray-medium; - } - } - - .instructions { - margin-bottom: 0.75em; - - p { - color: $color-gray-medium; - font-size: $font-size-small; - } - } - - .sizer { - padding-bottom: 1.5em; - visibility: hidden; - z-index: $layer-normal - 1; - } - } - - .waiting { - position: relative; min-height: 20em; width: 100%; - - img { - position: absolute; top: 50%; left: 50%; - @include transform(translate(-50%, -50%)); - } - } -} diff --git a/src/scss/templates/minimal_recipe.scss b/src/scss/templates/minimal_recipe.scss deleted file mode 100644 index 3a72470c8..000000000 --- a/src/scss/templates/minimal_recipe.scss +++ /dev/null @@ -1,63 +0,0 @@ -/* -Crafting Table - minimal_recipe.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -.view__minimal_recipe { - position: relative; height: 20em; width: 26em; - - .input { - position: absolute; top: 50%; left: 0; - @include transform(translateY(-50%)); - - .tool { - position: absolute; right: 0; bottom: -2em; left: 0; height: 1.5em; - text-align: center; - - a { - color: $color-text; - font-family: $font-family-normal; - font-size: $font-size-normal; - font-weight: bold; - text-decoration: none; - - &:hover { - color: $color-link; - text-decoration: underline; - } - } - } - } - - .output { - position: absolute; top: 50%; right: 0; height: 5.3em; width: 5.3em; - @include transform(translateY(-50%)); - - background: $color-gray-faint; - border: 0.2em solid $color-gray-medium; - padding: 0.1em; - - a { - position: absolute; top: 50%; left: 50%; height: 4.8em; width: 4.8em; - @include transform(translate(-50%, -50%)); - } - - .quantity { - position: absolute; right: 0.1em; bottom: 0; - color: white; - font-family: $font-family-header; - font-size: $font-size-large; - text-shadow: -2px -2px 0 #000, 2px -2px 0 #000, -2px 2px 0 #000, 2px 2px 0 #000; - } - } - - .multiplier { - position: absolute; top: 50%; right: 0; width: 2.7em; - @include transform(translateY(-50%) translateY(2.5em)); - font-family: $font-family-header; - font-size: $font-size-large; - text-align: center; - } -} diff --git a/src/scss/templates/mod.scss b/src/scss/templates/mod.scss deleted file mode 100644 index 66133028e..000000000 --- a/src/scss/templates/mod.scss +++ /dev/null @@ -1,48 +0,0 @@ -/* -Crafting Guide - mod.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__mod { - a { - background: $color-background-panel; - color: $color-text; - display: flex; - min-height: 16em; - padding: 1.2em; - text-decoration: none; - - &:hover { - border: 0.2em solid $color-link; - padding: 1.0em; - - h3 { - color: $color-link; - text-decoration: underline; - } - } - - .left { - flex: 0 0 33%; - padding: 0.5em; - - img { - max-width: calc(100% - 1.0em); - } - } - - .right { - flex: 1 1 66%; - - h3 { - font-size: $font-size-normal; - } - - .description { - margin-top: 1em; - } - } - } -} diff --git a/src/scss/templates/mod_pack.scss b/src/scss/templates/mod_pack.scss deleted file mode 100644 index a50f29d2a..000000000 --- a/src/scss/templates/mod_pack.scss +++ /dev/null @@ -1,33 +0,0 @@ -/* -Crafting Guide - mod_versions.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -.view__mod_pack { - - input { - border: 0; font-size: 1.5em; width: 90%; - } - - .mods { - position: relative; width: 100%; - padding: 1em; - } - - .panel { - background: white; - } - - .toolbar { - position: relative; width: 100%; - margin-top: 1em; - padding: 1em 1em; - text-align: left; - - button { - position: relative; width: 20em; - } - } -} diff --git a/src/scss/templates/mod_page.scss b/src/scss/templates/mod_page.scss deleted file mode 100644 index 9550f6b5d..000000000 --- a/src/scss/templates/mod_page.scss +++ /dev/null @@ -1,41 +0,0 @@ -/* -Crafting Guide - mod_page.scss - -Copyright (c) 2014 by Redwood Labs -All rights reserved. -*/ - -.view__mod_page { - & > div { - vertical-align: top; - display: inline-block; - } - - .sidebar { - .version { - position: relative; width: 80%; - margin: 0 10%; - margin-bottom: 1em; - } - } - - .mainBody { - - .description { - margin-bottom: 4em; - - p { - font-family: $font-family-normal; - font-size: $font-size-large; - } - } - - .itemGroups { - margin-top: 2em; - } - } - - .view__item { - position: relative; width: 33%; - } -} diff --git a/src/scss/templates/mod_selector.scss b/src/scss/templates/mod_selector.scss deleted file mode 100644 index daf63e83a..000000000 --- a/src/scss/templates/mod_selector.scss +++ /dev/null @@ -1,36 +0,0 @@ -/* -Crafting Table - mod.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -.view__mod_selector { - position: relative; width: 100%; - display: table-row; - - div, p { - display: table-cell; - padding: 0.4em; - } - - .version { - width: 12em; - - select { - position: relative; width: 100%; - } - } - - .name { - width: 18em; - - p { - text-decoration: underline; - } - } - - &.disabled { - p { color: $color-gray-light; } - } -} diff --git a/src/scss/templates/multiblock_viewer.scss b/src/scss/templates/multiblock_viewer.scss deleted file mode 100644 index 1db1f3326..000000000 --- a/src/scss/templates/multiblock_viewer.scss +++ /dev/null @@ -1,61 +0,0 @@ -/* -Crafting Guide - mod.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__multiblock_viewer { - display: flex; - align-items: stretch; - - h3 { - margin-bottom: 1em; - margin-left: 0; - } - - .left { - border-right: 1px solid $color-gray-light; - flex: 1 0 40%; - padding: 2em 0 0 2em; - } - - .right { - display: flex; - flex-direction: column; - flex: 0 1 60%; - - .caption { - display: flex; - justify-content: center; - align-items: center; - margin-top: 1em; - - img { - border: none; - margin-right: 1em; - height: 3.6em; - max-width: 3.6em; - } - - p { - font-weight: bold; - } - } - - .view__multiblock_viewer { - flex: 1 1 100%; - } - - .buttons { - display: flex; - flex: 0 0 auto; - margin: 1em 10% 0 10%; - - .button { - flex: 50%; - margin: 1em; - } - } - } -} diff --git a/src/scss/templates/slot.scss b/src/scss/templates/slot.scss deleted file mode 100644 index 8a5b8e057..000000000 --- a/src/scss/templates/slot.scss +++ /dev/null @@ -1,18 +0,0 @@ -/* -Crafting Guide - slot.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__slot { - position: relative; - - .quantity { - position: absolute; right: 0.1em; bottom: 0; - color: white; - font-family: $font-family-header; - font-size: $font-size-large; - text-shadow: -2px -2px 0 #000, 2px -2px 0 #000, -2px 2px 0 #000, 2px 2px 0 #000; - } -} diff --git a/src/scss/templates/stack.scss b/src/scss/templates/stack.scss deleted file mode 100644 index a3ae0ee45..000000000 --- a/src/scss/templates/stack.scss +++ /dev/null @@ -1,157 +0,0 @@ -/* -Crafting Guide - stack.scss - -Copyright (c) 2014-2015 by Redwood Labs -All rights reserved. -*/ - -.view__stack { - display: flex; - flex-direction: row; - align-items: baseline; - - font-family: $font-family-normal; - - .quantity { - flex: 0 0 auto; - - .bubble { - border: 0.1em solid $color-gray-light; - border-radius: 1.5em; - background: $color-ice; - - input { - width: 3em; - background: none; - border: none; - color: $color-background-panel; - font-family: $font-family-normal; - font-size: $font-size-normal; - font-weight: bold; - line-height: $font-size-normal; - outline: none; - text-align: center; - } - - &.editable:hover, &.editing { - background: $color-background-panel; - - input { - color: $color-text; - font-family: $font-family-input; - font-weight: normal; - } - } - } - } - - .icon { - flex: 0 0 auto; - margin: 0 0.5em; - - img { - width: 100%; height: auto; - max-width: 3.6em; - @include pixel-image; - } - } - - .name { - flex: 1 0 auto; - - a { - color: $color-text; - font-size: $font-size-normal; - text-decoration: none; - - &:hover { - color: $color-active-hover; - text-decoration: underline; - } - } - } - - .action { - display: flex; - flex-direction: row; - justify-content: flex-end; - - button { - position: relative; width: 3.0em; height: 3.0em; - - border: 0; - font-size: $font-size-small; - margin: 0; - outline: none; - padding: 0; - - &.check { - background: url('/images/check.png') no-repeat center; - - &:active { - background: url('/images/check_active.png') no-repeat center; - } - - &:disabled { - background: url('/images/check_disabled.png') no-repeat center !important; - cursor: inherit; - } - - &:hover { - background: url('/images/check_hover.png') no-repeat center; - } - } - - &.down { - background: url('/images/down.png') no-repeat center; - - &:active { - background: url('/images/down_active.png') no-repeat center; - } - - &:disabled { - background: url('/images/down_disabled.png') no-repeat center !important; - cursor: inherit; - } - - &:hover { - background: url('/images/down_hover.png') no-repeat center; - } - } - - &.remove { - background: url('/images/remove.png') no-repeat center; - - &:active { - background: url('/images/remove_active.png') no-repeat center; - } - - &:disabled { - background: url('/images/remove_disabled.png') no-repeat center !important; - cursor: inherit; - } - - &:hover { - background: url('/images/remove_hover.png') no-repeat center; - } - } - - &.up { - background: url('/images/up.png') no-repeat center; - - &:active { - background: url('/images/up_active.png') no-repeat center; - } - - &:disabled { - background: url('/images/up_disabled.png') no-repeat center !important; - cursor: inherit; - } - - &:hover { - background: url('/images/up_hover.png') no-repeat center; - } - } - } - } -} diff --git a/src/scss/templates/step.scss b/src/scss/templates/step.scss deleted file mode 100644 index 2f1896fed..000000000 --- a/src/scss/templates/step.scss +++ /dev/null @@ -1,51 +0,0 @@ -/* -Crafting Page - step.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__step { - display: flex; - flex-direction: column; - border-top: 0.1em solid $color-gray-medium; - padding: 1em 0; - - &:first-child { - border-top: 0; - padding-top: 0; - } - - &:hover { - .buttons { - opacity: 1.0; - } - } - - h3 { - margin-bottom: 1em; - } - - .main_content { - display: flex; - margin: 0 3em 2em 3em; - - .view__inventory { - flex: 60%; - } - - .view__minimal_recipe { - flex: 40%; - } - } - - .buttons { - display: flex; - opacity: 0; - transition: opacity $animate-normal; - - .button { - flex: 50%; - } - } -} \ No newline at end of file diff --git a/src/scss/templates/tutorial.scss b/src/scss/templates/tutorial.scss deleted file mode 100644 index 2d4065e69..000000000 --- a/src/scss/templates/tutorial.scss +++ /dev/null @@ -1,28 +0,0 @@ -/* -Crafting Guide - tutorial.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__tutorial { - position: relative; - display: inline-block; - margin-left: 1em; - vertical-align: top; - - &:first-child { - margin-left: 0; - } - - .caption { - position: relative; width: 100%; - display: block; - - p { - margin-top: 0.5em; - font-weight: bold; - text-align: center; - } - } -} \ No newline at end of file diff --git a/src/scss/templates/video.scss b/src/scss/templates/video.scss deleted file mode 100644 index 3e6d8eb3f..000000000 --- a/src/scss/templates/video.scss +++ /dev/null @@ -1,32 +0,0 @@ -/* -Crafting Guide - video.scss - -Copyright (C) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__video { - position: relative; - display: inline-block; - margin-left: 1em; - vertical-align: top; - - &:first-child { - margin-left: 0; - } - - iframe { - display: block; - } - - .caption { - position: relative; width: 100%; - display: block; - - p { - margin-top: 0.5em; - font-weight: bold; - text-align: center; - } - } -} \ No newline at end of file diff --git a/src/scss/views.scss b/src/scss/views.scss deleted file mode 100644 index 0ab6b691d..000000000 --- a/src/scss/views.scss +++ /dev/null @@ -1,144 +0,0 @@ -/* -Crafting Guide - views.scss - -Copyright (c) 2015 by Redwood Labs -All rights reserved. -*/ - -.view__footer { - background: $color-footer; - color: $color-footer-text; - margin-top: 2em; - - a { - color: $color-footer-text; - } - - .divider { - position: relative; height: 3.2em; width: 100%; - clear: both; - } - - .divider.top { - background: $color-dirt url('/images/grass_side.png'); - } - - .left, .center, .right { - position: relative; width: 33%; height: 23em; - float: left; - padding: 2em; - - .action { - position: absolute; bottom: 3em; left: 50%; - @include transform(translateX(-50%)); - } - } - - .divider.bottom { - background: $color-bedrock url('/images/bedrock.png'); - } -} - -.view__header { - background: $color-gray-light; - position: relative; height: 13em; - margin-top: 3.2em; - - h1 { - position: relative; top: -1.6em; left: -1.6em; - - p { - position: relative; top: 0.2em; - } - } - - .divider { - background: $color-brick-dark url('/images/stone_brick.png'); - position: absolute; bottom: 5em; height: 3.2em; width: 100%; - - .login { - position: absolute; top: 50%; right: 2em; - @include transform(translateY(-50%)); - - a { - color: $color-text-light; - font-family: $font-family-normal; - font-size: $font-size-normal; - font-weight: bold; - } - - .name { - color: $color-text-light; - font-family: $font-family-normal; - font-size: $font-size-normal; - margin-right: 2em; - } - } - } - - .navBar { - position: absolute; right: 2em; bottom: 1em; left: 2em; height: 3em; - - a { - position: relative; height: 3em; width: 15em; - background: $color-gray-faint; - border: 0.1em solid $color-gray-medium; - border-radius: 0 1.5em 1.5em 0; - cursor: pointer; - display: inline-block; - margin-left: -1.5em; - - transition: background $animate-normal; - - &:first-child { - border-radius: 1.5em; - margin-left: 0; - } - - &:hover { - background: $color-background-panel; - } - - &.selected { - background: $color-active; - - p { - color: $color-background-panel; - } - } - - .dot { - position: absolute; top: 50%; right: 1em; height: 1.5em; width: 1.5em; - @include transform(translateY(-50%)); - - background: $color-active; - border-radius: 0.75em; - opacity: 0; - } - - p { - position: absolute; top: 50%; left: 50%; width: 100%; - @include transform(translateX(-50%) translateY(-50%)); - - color: $color-active; - font-family: $font-family-normal; - font-size: $font-size-normal; - font-weight: bold; - text-align: center; - vertical-align: middle; - - transition: color $animate-normal; - } - } - - .view__item_selector { - position: absolute; top: 0; right: 0; height: 3em; width: 35em; - } - } -} - -.view__screen { - position: fixed; top: 0; right: 0; bottom: 0; left: 0; - display: none; - z-index: $layer-screen; -} diff --git a/src/server/crafting_guide_server.coffee b/src/server/crafting_guide_server.coffee new file mode 100644 index 000000000..286542353 --- /dev/null +++ b/src/server/crafting_guide_server.coffee @@ -0,0 +1,43 @@ +# +# Crafting Guide - crafting_guide_server.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +express = require 'express' +http = require 'http' +middleware = require './middleware' +routes = require './routes' + +############################################################################################################ + +module.exports = class CraftingGuideServer + + constructor: (port)-> + if not port? then throw new Error 'port is mandatory' + if not _.isNumber port then throw new Error 'port must be a number' + @port = parseInt port + + app = express() + app.disable 'etag' + + middleware.installBefore app + app.use routes + middleware.installAfter app + + @httpServer = http.createServer app + + start: -> + w.promise (resolve, reject)=> + @httpServer.once 'error', (error)-> reject error + @httpServer.listen @port, => + console.log "http://... ready on port #{@port}" + console.log "CraftingGuide is ready.\n\n" + resolve this + + stop: -> + w.promise (resolve, reject)=> + console.log "CraftingGuide is shutting down" + @httpServer.close() => + resolve this diff --git a/src/server/middleware.coffee b/src/server/middleware.coffee new file mode 100644 index 000000000..216ce1083 --- /dev/null +++ b/src/server/middleware.coffee @@ -0,0 +1,73 @@ +# +# Crafting Guide - middleware.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +bodyParser = require 'body-parser' +clientSessions = require 'client-sessions' +express = require 'express' +w = require 'when' + +############################################################################################################ + +exports.installBefore = (app)-> + app.use m for m in [ + bodyParser.json + limit: '1024kb' + clientSessions + cookieName: 'session-cookie' + duration: 1000 * 60 * 60 * 24 * 7 * 2 # 2 weeks in ms + secret: '8QmZ9KbBtN,^%9QT' + logRequest + prevent304 + promisify + ] + +exports.installAfter = (app)-> + app.use '/data', express.static '../../crafting-guide-data/data/', etag:false, maxAge: 0 + app.use express.static './static', etag: false, maxAge: 0 + +# Middleware Functions ##################################################################################### + +logRequest = (request, response, next)-> + console.log ">>>>> #{request.method} #{request.url}" + + receivedAt = Date.now() + totalBytes = 0 + + originalWrite = response.write + response.write = (chunk)-> + totalBytes += chunk.length if chunk?.length? + originalWrite.apply response, arguments + + originalEnd = response.end + response.end = (chunk)-> + totalBytes += chunk.length if chunk?.length? + + duration = Date.now() - receivedAt + sizeText = if totalBytes > 1024 then "#{(totalBytes / 1024.0).toFixed(2)} kB" else "#{totalBytes} B" + console.log "<<<<< #{request.method} #{request.url} responded " + + "#{response.statusCode} after #{duration}ms with #{sizeText}\n" + originalEnd.apply response, arguments + + next() + +prevent304 = (request, response, next)-> + response.setHeader 'Last-Modified', new Date().toUTCString() + next() + +promisify = (request, response, next)-> + response.sendPromise = (func)-> + w.try func + .then (result)-> + responseText = JSON.stringify result + console.log "#{responseText}" + response.send responseText + .catch (error)-> + console.error "Request failed with error:\n#{error.stack}" + response.status 500 + response.send message:error.message, stack:error.stack + .done() + next() diff --git a/src/server/routes.coffee b/src/server/routes.coffee new file mode 100644 index 000000000..d49699730 --- /dev/null +++ b/src/server/routes.coffee @@ -0,0 +1,20 @@ +# +# Crafting Guide - routes.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +express = require 'express' + +############################################################################################################ + +module.exports = router = express.Router() + +sendIndex = (request, response)-> + response.sendFile 'index.html', root: 'static' + +router.get '/browse*', sendIndex +router.get '/craft*', sendIndex +router.get '/login*', sendIndex +router.get '/news*', sendIndex diff --git a/src/server/server.coffee b/src/server/server.coffee new file mode 100644 index 000000000..b99370222 --- /dev/null +++ b/src/server/server.coffee @@ -0,0 +1,26 @@ +# +# Crafting Guide - server.coffee +# +# Copyright © 2014-2016 by Redwood Labs +# All rights reserved. +# + +CraftingGuideServer = require './crafting_guide_server' + +######################################################################################################################## + +global._ = require './underscore' +global.c = require './constants' +global.w = require 'when' + +######################################################################################################################## + +port = parseInt process.argv[2] +port = if _.isNaN port then c.server.defaultPort else port + +server = new CraftingGuideServer port +server.start() + +process.on 'SIGINT', -> + server.stop().finally -> + process.exit() diff --git a/src/test_helper.coffee b/src/test_helper.coffee new file mode 100644 index 000000000..e5a1a7bfc --- /dev/null +++ b/src/test_helper.coffee @@ -0,0 +1,31 @@ +### +# Crafting Guide - test.coffee +# +# Copyright (c) 2014-2015 by Redwood Labs +# All rights reserved. +### + +# Test Set-up ########################################################################################################## + +chai = require 'chai' +chai.use require 'sinon-chai' +chai.config.includeStack = true + +global.$ = require 'jquery' +global._ = require './common/underscore' +global.assert = chai.assert +global.c = require './common/constants' +global.expect = chai.expect +global.inspect = require('util').inspect +global.should = chai.should() +global.sinon = require 'sinon' +global.util = require 'util' +global.w = require 'when' +global.ε = 0.0001 +global.π = Math.PI + +global.Backbone = Backbone = require 'backbone' +Backbone.$ = $ + +{Logger} = require 'crafting-guide-common' +global.logger = new Logger level:Logger.FATAL diff --git a/static/fonts/press_start.ttf b/static/fonts/press_start.ttf deleted file mode 100644 index 1efa15873..000000000 Binary files a/static/fonts/press_start.ttf and /dev/null differ diff --git a/static/images/bookshelf.png b/static/images/bookshelf.png deleted file mode 100644 index 896c30e19..000000000 Binary files a/static/images/bookshelf.png and /dev/null differ diff --git a/static/images/boots.png b/static/images/boots.png deleted file mode 100644 index d6d18eca8..000000000 Binary files a/static/images/boots.png and /dev/null differ diff --git a/static/images/check.png b/static/images/check.png deleted file mode 100644 index 399c54fbd..000000000 Binary files a/static/images/check.png and /dev/null differ diff --git a/static/images/check_active.png b/static/images/check_active.png deleted file mode 100644 index 76e31f674..000000000 Binary files a/static/images/check_active.png and /dev/null differ diff --git a/static/images/check_disabled.png b/static/images/check_disabled.png deleted file mode 100644 index 31727dfc9..000000000 Binary files a/static/images/check_disabled.png and /dev/null differ diff --git a/static/images/check_hover.png b/static/images/check_hover.png deleted file mode 100644 index 8911dc7c0..000000000 Binary files a/static/images/check_hover.png and /dev/null differ diff --git a/static/images/chest_front.png b/static/images/chest_front.png deleted file mode 100644 index 3e1782e43..000000000 Binary files a/static/images/chest_front.png and /dev/null differ diff --git a/static/images/dirt.png b/static/images/dirt.png deleted file mode 100644 index 28f300b8a..000000000 Binary files a/static/images/dirt.png and /dev/null differ diff --git a/static/images/down.png b/static/images/down.png deleted file mode 100644 index 3c576c1ac..000000000 Binary files a/static/images/down.png and /dev/null differ diff --git a/static/images/down_active.png b/static/images/down_active.png deleted file mode 100644 index d12415468..000000000 Binary files a/static/images/down_active.png and /dev/null differ diff --git a/static/images/down_disabled.png b/static/images/down_disabled.png deleted file mode 100644 index a9a82fad9..000000000 Binary files a/static/images/down_disabled.png and /dev/null differ diff --git a/static/images/down_hover.png b/static/images/down_hover.png deleted file mode 100644 index 99aadeb67..000000000 Binary files a/static/images/down_hover.png and /dev/null differ diff --git a/static/images/fishing_rod.png b/static/images/fishing_rod.png deleted file mode 100644 index 1c858c8d8..000000000 Binary files a/static/images/fishing_rod.png and /dev/null differ diff --git a/static/images/paper.png b/static/images/paper.png deleted file mode 100644 index 13332d940..000000000 Binary files a/static/images/paper.png and /dev/null differ diff --git a/static/images/question.png b/static/images/question.png deleted file mode 100644 index 15481c2ab..000000000 Binary files a/static/images/question.png and /dev/null differ diff --git a/static/images/question_disabled.png b/static/images/question_disabled.png deleted file mode 100644 index 6f8cf0da6..000000000 Binary files a/static/images/question_disabled.png and /dev/null differ diff --git a/static/images/question_hover.png b/static/images/question_hover.png deleted file mode 100644 index f8e9db3d6..000000000 Binary files a/static/images/question_hover.png and /dev/null differ diff --git a/static/images/remove.png b/static/images/remove.png deleted file mode 100644 index af5f9b970..000000000 Binary files a/static/images/remove.png and /dev/null differ diff --git a/static/images/remove_action.png b/static/images/remove_action.png deleted file mode 100644 index ca0e6d17e..000000000 Binary files a/static/images/remove_action.png and /dev/null differ diff --git a/static/images/remove_disabled.png b/static/images/remove_disabled.png deleted file mode 100644 index 94e4e8d4c..000000000 Binary files a/static/images/remove_disabled.png and /dev/null differ diff --git a/static/images/remove_hover.png b/static/images/remove_hover.png deleted file mode 100644 index a6284d4fe..000000000 Binary files a/static/images/remove_hover.png and /dev/null differ diff --git a/static/images/stone_brick_light.png b/static/images/stone_brick_light.png deleted file mode 100644 index aac7c0ee6..000000000 Binary files a/static/images/stone_brick_light.png and /dev/null differ diff --git a/static/images/up.png b/static/images/up.png deleted file mode 100644 index 9369cb5cc..000000000 Binary files a/static/images/up.png and /dev/null differ diff --git a/static/images/up_active.png b/static/images/up_active.png deleted file mode 100644 index f9d1e8dde..000000000 Binary files a/static/images/up_active.png and /dev/null differ diff --git a/static/images/up_disabled.png b/static/images/up_disabled.png deleted file mode 100644 index e2b782cf3..000000000 Binary files a/static/images/up_disabled.png and /dev/null differ diff --git a/static/images/up_hover.png b/static/images/up_hover.png deleted file mode 100644 index 6cbefc0c7..000000000 Binary files a/static/images/up_hover.png and /dev/null differ diff --git a/static/images/workbench_top.png b/static/images/workbench_top.png deleted file mode 100644 index 60d8026c3..000000000 Binary files a/static/images/workbench_top.png and /dev/null differ diff --git a/test/test_helper.coffee b/test/test_helper.coffee deleted file mode 100644 index 1741653a7..000000000 --- a/test/test_helper.coffee +++ /dev/null @@ -1,28 +0,0 @@ -### -# Crafting Guide - test.coffee -# -# Copyright (c) 2014-2015 by Redwood Labs -# All rights reserved. -### - -# Test Set-up ########################################################################################################## - -chai = require 'chai' -chai.use require 'sinon-chai' -chai.config.includeStack = true - -global._ = require 'underscore' -global.Backbone = require 'backbone' -global.assert = chai.assert -global.expect = chai.expect -global.inspect = require('util').inspect -global.should = chai.should() -global.sinon = require 'sinon' -global.util = require 'util' -global.w = require 'when' - -{Logger} = require 'crafting-guide-common' -global.logger = new Logger level:Logger.FATAL - -require '../src/coffee/polyfill' -require '../src/coffee/underscore_mixins' diff --git a/vendor/email.js b/vendor/email.js new file mode 100644 index 000000000..ae8e2538b --- /dev/null +++ b/vendor/email.js @@ -0,0 +1,412 @@ +(function() { + "use strict"; + + function t(t) { + return "function" == typeof t || "object" == typeof t && null !== t + } + + function e(t) { + return "function" == typeof t + } + + function n(t) { + return "object" == typeof t && null !== t + } + + function r(t) { + U = t + } + + function o(t) { + J = t + } + + function s() { + return function() { + process.nextTick(f) + } + } + + function i() { + return function() { + R(f) + } + } + + function u() { + var t = 0, + e = new z(f), + n = document.createTextNode(""); + return e.observe(n, { + characterData: !0 + }), + function() { + n.data = t = ++t % 2 + } + } + + function a() { + var t = new MessageChannel; + return t.port1.onmessage = f, + function() { + t.port2.postMessage(0) + } + } + + function c() { + return function() { + setTimeout(f, 1) + } + } + + function f() { + for (var t = 0; X > t; t += 2) { + var e = V[t], + n = V[t + 1]; + e(n), V[t] = void 0, V[t + 1] = void 0 + } + X = 0 + } + + function l() { + try { + var t = require, + e = t("vertx"); + return R = e.runOnLoop || e.runOnContext, i() + } catch (t) { + return c() + } + } + + function p() {} + + function d() { + return new TypeError("You cannot resolve a promise with itself") + } + + function h() { + return new TypeError("A promises callback cannot return that same promise.") + } + + function v(t) { + try { + return t.then + } catch (t) { + return et.error = t, et + } + } + + function _(t, e, n, r) { + try { + t.call(e, n, r) + } catch (t) { + return t + } + } + + function m(t, e, n) { + J(function(t) { + var r = !1, + o = _(n, e, function(n) { + r || (r = !0, e !== n ? w(t, n) : j(t, n)) + }, function(e) { + r || (r = !0, x(t, e)) + }, "Settle: " + (t._label || " unknown promise")); + !r && o && (r = !0, x(t, o)) + }, t) + } + + function y(t, e) { + e._state === $ ? j(t, e._result) : e._state === tt ? x(t, e._result) : A(e, void 0, function(e) { + w(t, e) + }, function(e) { + x(t, e) + }) + } + + function g(t, n) { + if (n.constructor === t.constructor) y(t, n); + else { + var r = v(n); + r === et ? x(t, et.error) : void 0 === r ? j(t, n) : e(r) ? m(t, n, r) : j(t, n) + } + } + + function w(e, n) { + e === n ? x(e, d()) : t(n) ? g(e, n) : j(e, n) + } + + function b(t) { + t._onerror && t._onerror(t._result), E(t) + } + + function j(t, e) { + t._state === Z && (t._result = e, t._state = $, 0 !== t._subscribers.length && J(E, t)) + } + + function x(t, e) { + t._state === Z && (t._state = tt, t._result = e, J(b, t)) + } + + function A(t, e, n, r) { + var o = t._subscribers, + s = o.length; + t._onerror = null, o[s] = e, o[s + $] = n, o[s + tt] = r, 0 === s && t._state && J(E, t) + } + + function E(t) { + var e = t._subscribers, + n = t._state; + if (0 !== e.length) { + for (var r, o, s = t._result, i = 0; i < e.length; i += 3) r = e[i], o = e[i + n], r ? L(n, r, o, s) : o(s); + t._subscribers.length = 0 + } + } + + function T() { + this.error = null + } + + function S(t, e) { + try { + return t(e) + } catch (t) { + return nt.error = t, nt + } + } + + function L(t, n, r, o) { + var s, i, u, a, c = e(r); + if (c) { + if (s = S(r, o), s === nt ? (a = !0, i = s.error, s = null) : u = !0, n === s) return void x(n, h()) + } else s = o, u = !0; + n._state !== Z || (c && u ? w(n, s) : a ? x(n, i) : t === $ ? j(n, s) : t === tt && x(n, s)) + } + + function P(t, e) { + try { + e(function(e) { + w(t, e) + }, function(e) { + x(t, e) + }) + } catch (e) { + x(t, e) + } + } + + function O(t, e) { + var n = this; + n._instanceConstructor = t, n.promise = new t(p), n._validateInput(e) ? (n._input = e, n.length = e.length, n._remaining = e.length, n._init(), 0 === n.length ? j(n.promise, n._result) : (n.length = n.length || 0, n._enumerate(), 0 === n._remaining && j(n.promise, n._result))) : x(n.promise, n._validationError()) + } + + function M(t) { + return new rt(this, t).promise + } + + function C(t) { + function e(t) { + w(o, t) + } + + function n(t) { + x(o, t) + } + var r = this, + o = new r(p); + if (!N(t)) return x(o, new TypeError("You must pass an array to race.")), o; + for (var s = t.length, i = 0; o._state === Z && s > i; i++) A(r.resolve(t[i]), void 0, e, n); + return o + } + + function F(t) { + var e = this; + if (t && "object" == typeof t && t.constructor === e) return t; + var n = new e(p); + return w(n, t), n + } + + function I(t) { + var e = this, + n = new e(p); + return x(n, t), n + } + + function q() { + throw new TypeError("You must pass a resolver function as the first argument to the promise constructor") + } + + function k() { + throw new TypeError("Failed to construct 'Promise': Please use the 'new' operator, this object constructor cannot be called as a function.") + } + + function B(t) { + this._id = at++, this._state = void 0, this._result = void 0, this._subscribers = [], p !== t && (e(t) || q(), this instanceof B || k(), P(this, t)) + } + + function D() { + var t; + if ("undefined" != typeof global) t = global; + else if ("undefined" != typeof self) t = self; + else try { + t = Function("return this")() + } catch (t) { + throw new Error("polyfill failed because global object is unavailable in this environment") + } + var e = t.Promise; + (!e || "[object Promise]" !== Object.prototype.toString.call(e.resolve()) || e.cast) && (t.Promise = ct) + } + var H; + H = Array.isArray ? Array.isArray : function(t) { + return "[object Array]" === Object.prototype.toString.call(t) + }; + var R, U, Y, N = H, + X = 0, + J = ({}.toString, function(t, e) { + V[X] = t, V[X + 1] = e, X += 2, 2 === X && (U ? U(f) : Y()) + }), + K = "undefined" != typeof window ? window : void 0, + W = K || {}, z = W.MutationObserver || W.WebKitMutationObserver, + G = "undefined" != typeof process && "[object process]" === {}.toString.call(process), + Q = "undefined" != typeof Uint8ClampedArray && "undefined" != typeof importScripts && "undefined" != typeof MessageChannel, + V = new Array(1e3); + Y = G ? s() : z ? u() : Q ? a() : void 0 === K && "function" == typeof require ? l() : c(); + var Z = void 0, + $ = 1, + tt = 2, + et = new T, + nt = new T; + O.prototype._validateInput = function(t) { + return N(t) + }, O.prototype._validationError = function() { + return new Error("Array Methods must be provided an Array") + }, O.prototype._init = function() { + this._result = new Array(this.length) + }; + var rt = O; + O.prototype._enumerate = function() { + for (var t = this, e = t.length, n = t.promise, r = t._input, o = 0; n._state === Z && e > o; o++) t._eachEntry(r[o], o) + }, O.prototype._eachEntry = function(t, e) { + var r = this, + o = r._instanceConstructor; + n(t) ? t.constructor === o && t._state !== Z ? (t._onerror = null, r._settledAt(t._state, e, t._result)) : r._willSettleAt(o.resolve(t), e) : (r._remaining--, r._result[e] = t) + }, O.prototype._settledAt = function(t, e, n) { + var r = this, + o = r.promise; + o._state === Z && (r._remaining--, t === tt ? x(o, n) : r._result[e] = n), 0 === r._remaining && j(o, r._result) + }, O.prototype._willSettleAt = function(t, e) { + var n = this; + A(t, void 0, function(t) { + n._settledAt($, e, t) + }, function(t) { + n._settledAt(tt, e, t) + }) + }; + var ot = M, + st = C, + it = F, + ut = I, + at = 0, + ct = B; + B.all = ot, B.race = st, B.resolve = it, B.reject = ut, B._setScheduler = r, B._setAsap = o, B._asap = J, B.prototype = { + constructor: B, + then: function(t, e) { + var n = this, + r = n._state; + if (r === $ && !t || r === tt && !e) return this; + var o = new this.constructor(p), + s = n._result; + if (r) { + var i = arguments[r - 1]; + J(function() { + L(r, o, i, s) + }) + } else A(n, o, t, e); + return o + }, + catch: function(t) { + return this.then(null, t) + } + }; + var ft = D, + lt = { + Promise: ct, + polyfill: ft + }; + "function" == typeof define && define.amd ? define(function() { + return lt + }) : "undefined" != typeof module && module.exports ? module.exports = lt : "undefined" != typeof this && (this.ES6Promise = lt), ft() +}).call(this); + +var emailjs = new function() { + var t = this; + this.version = "0.1", this.secure = !0, this.server = "api.emailjs.com", this.init = function(e, n, r) { + t.user_id = e, "undefined" != typeof n && (t.server = n), "undefined" != typeof r && (t.secure = r) + }, this.send = function(e, n, r, o) { + var s = t.secure ? "https:" : "http:", + i = [s, "", t.server, "api/v1.0/email/send"].join("/"); + if (document.getElementById("g-recaptcha-response")) var u = document.getElementById("g-recaptcha-response").value || null; + return new Promise(function(s, a) { + var c = new XMLHttpRequest; + c.open("POST", i), c.setRequestHeader("Content-Type", "application/json;charset=UTF-8"), c.onload = function() { + 200 == this.status ? s({ + status: c.status, + text: c.responseText + }) : a({ + status: c.status, + text: c.responseText + }) + }, c.onerror = function() { + a({ + status: c.status, + text: c.responseText + }) + }, u && (r["g-recaptcha-response"] = u); + var f = { + user_id: o || t.user_id, + service_id: e, + template_id: n, + template_params: r + }; + c.send(JSON.stringify(f)) + }) + }, this.sendForm = function(e, n, r, o) { + var s = null, + i = null; + if ("undefined" != typeof o && o) i = o; + else { + if ("undefined" == typeof t.user_id || !t.user_id) throw "Error. User ID not found."; + i = t.user_id + } if ("undefined" == typeof r || !r) throw "Error. Form id/object not found."; + if ("string" == typeof r) s = document.getElementById(r); + else { + if ("object" != typeof r) throw "Error. invalid form type"; + s = r + } + s.classList.remove("emailjs-sending"), s.classList.remove("emailjs-success"), s.classList.remove("emailjs-error"); + var u = t.secure ? "https:" : "http:", + a = [u, "", t.server, "api/v1.0/email/send-form"].join("/"); + return new Promise(function(t, r) { + s.classList.add("emailjs-sending"); + var o = new XMLHttpRequest; + o.open("POST", a, !0), o.onload = function() { + s.classList.remove("emailjs-sending"), 200 == this.status ? (s.classList.add("emailjs-success"), t({ + status: o.status, + text: o.responseText + })) : (s.classList.add("emailjs-error"), r({ + status: o.status, + text: o.responseText + })) + }, o.onerror = function() { + s.classList.add("emailjs-error"), r({ + status: o.status, + text: o.responseText + }) + }; + var u = new FormData(s); + u.append("user_id", i), u.append("service_id", e), u.append("template_id", n), o.send(u) + }) + } + }; + +module.exports = emailjs \ No newline at end of file