├── .DS_Store ├── .gitignore ├── CONTRIBUTING.md ├── LICENSE ├── README.md ├── about └── index.html ├── asset ├── dist │ └── shipit.min.css ├── fonts │ ├── FontAwesome.otf │ ├── averta-bold.woff │ ├── averta-bold.woff2 │ ├── averta-regular.woff │ ├── averta-regular.woff2 │ ├── fontawesome-webfont.eot │ ├── fontawesome-webfont.svg │ ├── fontawesome-webfont.ttf │ ├── fontawesome-webfont.woff │ └── fontawesome-webfont.woff2 ├── js │ ├── app.js │ ├── config.dev.js │ ├── config.prod.js │ ├── newShip.js │ └── render.js └── sass │ ├── base │ └── _font.scss │ ├── main.scss │ └── style.scss ├── gulpfile.js ├── icons ├── apple-touch-icon-114x114.png ├── apple-touch-icon-120x120.png ├── apple-touch-icon-144x144.png ├── apple-touch-icon-152x152.png ├── apple-touch-icon-57x57.png ├── apple-touch-icon-60x60.png ├── apple-touch-icon-72x72.png ├── apple-touch-icon-76x76.png ├── code.txt ├── favicon-128.png ├── favicon-16x16.png ├── favicon-196x196.png ├── favicon-32x32.png ├── favicon-96x96.png ├── favicon.ico ├── mstile-144x144.png ├── mstile-150x150.png ├── mstile-310x150.png ├── mstile-310x310.png └── mstile-70x70.png ├── index.html ├── new └── index.html ├── package-lock.json └── package.json /.DS_Store: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/.DS_Store -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules/* -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | # Contribution Guidelines 2 | 3 | This document contains a set of guidelines which any contributions to *any* Hack Club repository must follow. 4 | 5 | [If you disagree with something here, you should open up an issue to discuss making a change!](https://github.com/hackclub/hackclub/issues/new) 6 | 7 | ## Contributing to the Workshops 8 | 9 | For more details specific to contributing a workshop, [look here](workshops/CONTRIBUTING.md). 10 | 11 | ## Table of Contents 12 | 13 | 1. [GitHub Flow](#github-flow) 14 | 2. [Branch Names](#branch-names) 15 | 3. [File Names](#file-names) 16 | 4. [Git Commits](#git-commits) 17 | 5. [Making a Pull Request](#making-a-pull-request) 18 | 19 | ## GitHub Flow 20 | 21 | We use a modified version of [GitHub Flow](https://guides.github.com/introduction/flow/) at Hack Club. The only difference is instead of deploying from a reviewed pull request, we merge first and deploy straight from master. 22 | 23 | Part of the GitHub Flow is submitting pull requests. See https://help.github.com/articles/using-pull-requests/ for a good overview of what pull requests are and how to use them. We use the _fork & pull model_ for managing contributions. 24 | 25 | ## Branch Names 26 | 27 | Branch names should adhere to the following: 28 | 29 | - All lowercase 30 | - `-` as space separator for branch names 31 | - If a feature branch, include the name of the feature 32 | 33 | ## File Names 34 | 35 | File names should follow the following guidelines: 36 | 37 | - All lowercase 38 | - `_` as space separator for file names 39 | - `-` as a space separator for dates in file names 40 | - Dates in `YY-MM-DD` format 41 | 42 | ## Git Commits 43 | 44 | In order to ensure that our git history makes sense we have certain guidelines which we require contributors to adhere to. These are: 45 | 46 | ### Commits should follow the commit standards 47 | 48 | These are: 49 | 50 | - Commits should be written in the imperative mood 51 | - Commits should start with a capital letter 52 | - Commits should not end with a full stop 53 | 54 | This is a style used by many other Open Source projects (Linux, Rails) as well as most corporate software development shops. 55 | 56 | [This is a great guide on writing a git commit message](http://chris.beams.io/posts/git-commit/) 57 | 58 | #### Examples 59 | 60 | > fix typo in introduction. 61 | 62 | - Does **not** start with a capital letter 63 | - Ends with a full stop 64 | 65 | > Added Iron Man GIF 66 | 67 | - Does **not** use the imperative mood 68 | 69 | > Adding more pizza parlors to directory 70 | 71 | - Does **not** use the imperative mood 72 | 73 | > Fix typo in introduction to user guide 74 | 75 | This commit message is wonderful! 76 | 77 | ### Commits should be one logically unit of change 78 | 79 | A logical unit of change can be thought of as completion of a single task. 80 | 81 | A good way to figure out if you are not adhering to this rule is to tell yourself what you changed ("I added a picture of a donkey to the Twilio workshop"). If you find yourself having multiple statements in this description then you have made your commit too big. 82 | 83 | #### Examples 84 | 85 | > Add an image of pizza, fix typos, rewrite `README.md` 86 | 87 | This commit message contains three units of change, they are: 88 | 89 | - An image of pizza 90 | - Fixed typos 91 | - Rewrote `README.md` 92 | 93 | These should be split into one commit each. 94 | 95 | > Add an image of pizza 96 | 97 | This commit is great as only one logical change was made. 98 | 99 | ### Commits should explain the change, but not be longer than 50 chars 100 | 101 | A commit message is used for quickly summarizing a change. Another contributor should be able to read it, along with the content and immediately understand the change does. 102 | 103 | #### Examples 104 | 105 | > Fix typo 106 | 107 | - This commit message does not give any context 108 | 109 | > Add the spark reactor source code into the document where we add our thoughts 110 | 111 | - This commit message is too long! It should be less than 50 characters! 112 | - It uses too many words and could be simplified 113 | 114 | ## Making a Pull Request 115 | 116 | Here are a series of GIFs that illustrate how to make and commit a change, and create a pull request for review, using GitHub's web interface. 117 | 118 | ![](img/gh_web_find_file.gif) 119 | 120 | ![](img/gh_web_edit_file.gif) 121 | 122 | ![](img/gh_web_make_commit.gif) 123 | 124 | ![](img/gh_web_submit_pr.gif) 125 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2017 Hack Club, Mingjie Jiang and Sean Kim 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Hack Club Shipit Platform 2 | ### Welcome to the new era of spaghetti one-pager. By [**@jsneak**][1] & [**@mj66**][2] 3 | [![Maintainability](https://api.codeclimate.com/v1/badges/7ad75aa411799aa0b842/maintainability)](https://codeclimate.com/github/hackclub/shipit/maintainability) 4 | [![Twitter Follow](https://img.shields.io/twitter/follow/starthackclub.svg?style=social&label=Follow)](https://twitter.com/starthackclub) 5 | 6 | ## About this platform 7 | The Shipit Platform runs on [Firebase][6], with other resources from [Rebrandly][7], [jQuery][8], [Font Awesome][9], [Handlebars.js][10], [Toastr.js][11], and a modified version of [Bulma.css][12]. Click on them to see their licenses. 8 | 9 | ## Shipit Community Guidelines 10 | Not much to explain: be appropriate, and respect other people's work. This includes your peer's posted projects and the platform. 11 | 12 | ### Things that you need to fill in for each submission: 13 | - **Name**: The name of the project. The name needs to be your actural project name, and a catchy title will get you more audiences! 14 | - **Author**: In most situations, this part is already filled with your GitHub profile name. Feel free to replace it with your GitHub handle, or your co-developer's name(s) and handle(s). 15 | - **Description**: Some details about your project. What is it supposed to do? How is it unique? How did you come up with the idea? If you were following a [Hack Club Workshop][3], include that, too. 16 | - **Live link**: A link linking to your working demo. If your project is not a website, link to your download page. 17 | - **Code link**: A link linking to the source code of your project. It can be a GitHub repository, a GitLab repository, or just a simple Cloud9 project. 18 | 19 | You should be following the [Hack Club Code of Conduct](https://github.com/hackclub/hackclub/blob/master/CONDUCT.md) at any time. 20 | 21 | ## Contributing & Debugging 22 | Contributions and exploitations are welcome! But since this platform may contain a lot of data, make sure you are following the following guidelines while contributing: 23 | 1. Check out the [Hack Club Contribution Guidelines][5]. Unless otherwise stated, please follow the same guidelines. 24 | 2. The commit messages do not need to be too formal... but please be informative, because it will make things easier for us. Aside from that, feel free to make us laugh! 25 | 3. Do not directly exploit on the running server. We'll be running a private server for active development, so when you think you’ve found a bug or a possible security vulnerbility, talk to us (@mj66 & @jsneak) first on slack! 26 | 4. If you would like another functionality on the platform, feel free to talk to us! The `#shipit-plat` channel on the Slack channel has been created for development discussions. 27 | 28 | ## Links 29 | - Check out [PROPHET ORPHEUS'S DIARY][4], a blog of the Shipit Platform where we post platform updates and featured projects periodically! 30 | 31 | ## License 32 | The Shipit Platform is open source under [the GNU General Public License v3.0][13]. 33 | 34 | 35 | [1]: https://github.com/JSneak 36 | [2]: https://github.com/mj66 37 | [3]: https://hackclub.com/workshops/ 38 | [4]: https://blog.shipit.tech/ 39 | [5]: https://github.com/hackclub/hackclub/blob/master/CONTRIBUTING.md 40 | [6]: https://firebase.google.com/ 41 | [7]: https://developers.rebrandly.com/ 42 | [8]: https://jquery.org/license/ 43 | [9]: http://fontawesome.io/license/ 44 | [10]: https://github.com/wycats/handlebars.js/blob/master/LICENSE 45 | [11]: http://codeseven.github.io/toastr/#license 46 | [12]: https://github.com/jgthms/bulma/blob/master/LICENSE 47 | [13]: https://github.com/mj66/shipit/blob/master/LICENSE 48 | -------------------------------------------------------------------------------- /about/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | Hack Club Shipit! 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 51 | 52 | 63 | 64 | 65 | 66 | 67 |
68 | 77 | 78 |
79 |
80 |
81 |
82 |

83 | Hack Club Shipit Platform 84 |

85 |

86 | A platform for hackers to show off their creations. 87 |

88 |
89 |
90 |
91 | 92 |
93 |

94 | About this platform

95 | 96 |

The Shipit Platform runs on 97 | Firebase, with other resources from 98 | Rebrandly, 99 | jQuery, 100 | Font Awesome, 101 | Handlebars.js, 102 | Toastr.js, and a modified version of 103 | Bulma.css. Click on them to see their licenses.

104 |

105 | Shipit Community Guidelines

106 |

Not much to explain: be appropriate, and respect other people’s work. This includes your peer’s posted projects 107 | and the platform.

108 |

109 | Things that you need to fill in for each submission:

110 |
    111 |
  • 112 | Name: The name of the project. The name needs to be your actural project name, and a catchy 113 | title will get you more audiences!
  • 114 |
  • 115 | Author: In most situations, this part is already filled with your GitHub profile name. Feel 116 | free to replace it with your GitHub handle, or your co-developer’s name(s) and handle(s).
  • 117 |
  • 118 | Description: Some details about your project. What is it supposed to do? How is it unique? 119 | How did you come up with the idea? If you were following a 120 | Hack Club Workshop, include that, too.
  • 121 |
  • 122 | Live link: A link linking to your working demo. If your project is not a website, link to 123 | your download page.
  • 124 |
  • 125 | Code link: A link linking to the source code of your project. It can be a GitHub repository, 126 | a GitLab repository, or just a simple Cloud9 project.
  • 127 |
128 |

You should be following the 129 | Hack Club Code of Conduct at any time.

130 |

131 | Contributing & Debugging

132 |

Contributions and exploitations are welcome! But since this platform may contain a lot of data, make sure 133 | you are following the following guidelines while contributing:

134 |
    135 |
  1. Check out the 136 | Hack Club Contribution Guidelines. Unless otherwise stated, please follow the same guidelines.
  2. 137 |
  3. The commit messages do not need to be too formal… but please be informative, because it will make things 138 | easier for us. Aside from that, feel free to make us laugh!
  4. 139 |
  5. Do not directly exploit on the running server. We’ll be running a private server for active development, 140 | so when you think you’ve found a bug or a possible security vulnerbility, talk to us (@mj66 & 141 | @jsneak) first on slack!
  6. 142 |
  7. If you would like another functionality on the platform, feel free to talk to us! The 143 | #shipit-plat channel on the Slack channel has been created for development discussions.
  8. 144 |
145 |

146 | License

147 |

The Shipit Platform is open source under 148 | the GNU General Public License v3.0.

149 |
150 | 151 | 152 | 173 | 174 | 175 |
176 |
177 | 178 | 179 | 180 | 181 | 182 | -------------------------------------------------------------------------------- /asset/fonts/FontAwesome.otf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/asset/fonts/FontAwesome.otf -------------------------------------------------------------------------------- /asset/fonts/averta-bold.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/asset/fonts/averta-bold.woff -------------------------------------------------------------------------------- /asset/fonts/averta-bold.woff2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/asset/fonts/averta-bold.woff2 -------------------------------------------------------------------------------- /asset/fonts/averta-regular.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/asset/fonts/averta-regular.woff -------------------------------------------------------------------------------- /asset/fonts/averta-regular.woff2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/asset/fonts/averta-regular.woff2 -------------------------------------------------------------------------------- /asset/fonts/fontawesome-webfont.eot: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/asset/fonts/fontawesome-webfont.eot -------------------------------------------------------------------------------- /asset/fonts/fontawesome-webfont.ttf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/asset/fonts/fontawesome-webfont.ttf -------------------------------------------------------------------------------- /asset/fonts/fontawesome-webfont.woff: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/asset/fonts/fontawesome-webfont.woff -------------------------------------------------------------------------------- /asset/fonts/fontawesome-webfont.woff2: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/asset/fonts/fontawesome-webfont.woff2 -------------------------------------------------------------------------------- /asset/js/app.js: -------------------------------------------------------------------------------- 1 | firebase.initializeApp(config); 2 | //Database Control 3 | const provider = new firebase.auth.GithubAuthProvider(); 4 | const database = firebase.database(); 5 | const projectsRef = database.ref("/projects"); 6 | const monthNames = ["January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"]; 7 | const query = database.ref("/projects").orderByChild("timestamp"); 8 | const connectedRef = database.ref(".info/connected"); 9 | const databaseRef = database.ref("/"); 10 | 11 | var isConnected, upvoteStatus = true; 12 | var projectsDisplayed = []; 13 | var firstName; 14 | var firstKnownKey, lastProjLoaded, queryIr = 0, 15 | sfired = false; 16 | 17 | firebase.auth().onAuthStateChanged(function (user) { 18 | if (user) { 19 | isLoggedIn(firebase.auth().currentUser); 20 | } 21 | else { 22 | isLoggedOut(); 23 | } 24 | }); 25 | 26 | function githubSignin() { 27 | firebase.auth().signInWithRedirect(provider) 28 | 29 | .then(function (result) { 30 | firstName = firebase.auth().currentUser.displayName.split(" ")[0]; 31 | checkForFirstTime(firebase.auth().currentUser.uid); 32 | //User Sucessfully Logged In 33 | toastr.success("Welcome, " + firstName + "!", "Successfully logged in."); 34 | 35 | }).catch(function (error) { 36 | var errorCode = error.code; 37 | var errorMessage = error.message; 38 | //User Log In Error 39 | toastr.error("Signin failed: " + errorCode + " - " + errorMessage); 40 | }); 41 | } 42 | 43 | function githubSignout() { 44 | firebase.auth().signOut() 45 | 46 | .then(function () { 47 | 48 | window.location.reload(); 49 | //User Log Out Successful, refresh page for content 50 | 51 | }, function (error) { 52 | 53 | toastr.error("Signout failed: " + error); 54 | 55 | //User Log Out Failed 56 | }); 57 | } 58 | 59 | function isLoggedOut() { 60 | $("#gh-logout").hide(); 61 | 62 | $("#logged-in-user").hide(); 63 | $("#logged-out-user").show(); 64 | } 65 | 66 | function isLoggedIn(user, token) { 67 | firstName = firebase.auth().currentUser.displayName.split(" ")[0]; 68 | 69 | //Google Analytics 70 | ga('set', 'userId', firebase.auth().currentUser.uid); // Set the user ID using signed-in user_id. 71 | 72 | $("#gh-logout").show(); 73 | 74 | closeShipper(); 75 | 76 | $("#userName").html(user.displayName); 77 | $("#fname-header").html(firstName + ", s"); 78 | $("#useravatar").attr("src", user.photoURL); 79 | loadUpVotedProjects(firebase.auth().currentUser.uid); 80 | loadFlaggedProjects(firebase.auth().currentUser.uid); 81 | 82 | $("#logged-in-user").show(); 83 | $("#logged-out-user").hide(); 84 | } 85 | 86 | function getSL(dest) { 87 | $.ajax({ 88 | url: "https://api.rebrandly.com/v1/links", 89 | type: "post", 90 | data: JSON.stringify({ 91 | "destination": "https://shipit.hackclub.com/?shared=" + dest, 92 | "domain": { 93 | "id": "c8e958cfc21c4a6d8b94ed1690e8cfc4" 94 | }, 95 | "title": "Shipit:" + firebase.auth().currentUser.displayName + " / " + firebase.auth().currentUser.uid + " / " + getTimeStamp(), 96 | "team": "11eb9668b45643aa8911a853f8f3e624" 97 | }), 98 | headers: { 99 | "team": "11eb9668b45643aa8911a853f8f3e624", 100 | "Content-Type": "application/json", 101 | "apikey": "1e766d2359454af3bdc8aa52353903a4", 102 | 103 | }, 104 | dataType: "json", 105 | success: function (link) { 106 | $("#share-id" + dest).attr("value", "https://" + link.shortUrl); 107 | $("#share-twitter" + dest).attr("onclick", "shareTwitter(\"https://" + link.shortUrl + "\")"); 108 | } 109 | }); 110 | } 111 | 112 | function shortLinkForSlack(author, name, plink, code, desc, ts, dest) { 113 | $.ajax({ 114 | url: "https://api.rebrandly.com/v1/links", 115 | type: "post", 116 | data: JSON.stringify({ 117 | "destination": "https://shipit.hackclub.com/?shared=" + dest, 118 | "domain": { 119 | "id": "c8e958cfc21c4a6d8b94ed1690e8cfc4" 120 | }, 121 | "title": "Shipit:" + firebase.auth().currentUser.displayName + " / " + firebase.auth().currentUser.uid + " / " + getTimeStamp(), 122 | "team": "11eb9668b45643aa8911a853f8f3e624" 123 | }), 124 | headers: { 125 | "team": "11eb9668b45643aa8911a853f8f3e624", 126 | "Content-Type": "application/json", 127 | "apikey": "1e766d2359454af3bdc8aa52353903a4", 128 | 129 | }, 130 | dataType: "json", 131 | success: function (link) { 132 | makeSlackCall(author, name, plink, code, desc, ts, "https://" + link.shortUrl); 133 | } 134 | }); 135 | } 136 | 137 | function shareTwitter(dest) { 138 | window.location.href = "http://twitter.com/share?text=Another wonderful project by a Hack Club member: &url=" + dest + "&via=starthackclub&related=starthackclub"; 139 | } 140 | 141 | 142 | function getParams(name, url) { 143 | if (!url) url = window.location.href; 144 | name = name.replace(/[\[\]]/g, "\\$&"); 145 | var regex = new RegExp("[?&]" + name + "(=([^&#]*)|&|#|$)"), 146 | results = regex.exec(url); 147 | if (!results) return null; 148 | if (!results[2]) return ''; 149 | return decodeURIComponent(results[2].replace(/\+/g, " ")); 150 | } 151 | 152 | $(function () { 153 | database.ref("/featured").once("value") 154 | .then(function (snapshot) { 155 | var featuredKey = snapshot.val()["featured"].toString(); 156 | 157 | var editorNotes = snapshot.val()["notes"].toString(); 158 | 159 | query.once("value").then(function (projSnap) { 160 | displayFeatured(projSnap.child(featuredKey).val(), featuredKey, editorNotes); 161 | }); 162 | 163 | }); 164 | 165 | var shared = getParams("shared"); 166 | if (shared != null) { 167 | getProp(shared); 168 | $("#launch").on("click", function () { 169 | window.location.replace("/?action=launch"); 170 | }); 171 | } 172 | else { 173 | 174 | query.limitToLast(10).on("child_added", function (snapshot) { 175 | if (!firstKnownKey) { 176 | firstKnownKey = snapshot.key; 177 | } 178 | displayProjects(snapshot.val(), snapshot.key); 179 | if (!lastProjLoaded) { 180 | lastProjLoaded = snapshot.val().timestamp; 181 | } 182 | }); 183 | 184 | 185 | } 186 | var action = getParams("action"); 187 | if (action == "launch") { 188 | openShipper(); 189 | } 190 | }); 191 | 192 | connectedRef.on("value", function (snapshot) { 193 | if (snapshot.val() == true) { 194 | isConnected = true; 195 | } 196 | else { 197 | isConnected = false; 198 | } 199 | }); 200 | 201 | 202 | function displayFeatured(data, key, ednote) { 203 | try { 204 | var newProject = { 205 | author: data.author, 206 | name: data.name, 207 | timestamp: convertTimestamp(data.timestamp), 208 | desc: data.desc, 209 | link: data.link, 210 | code: data.code, 211 | upvote: data.upvote, 212 | ednote: ednote, 213 | uid: key 214 | } 215 | loadFeatured(newProject); 216 | $("#project" + key).css("display", "none"); 217 | } 218 | catch (e) { 219 | console.log("Warning: Unknown error occured. The content is successfully rendered."); 220 | console.log(e); 221 | } 222 | } 223 | 224 | function displayProjects(data, key) { 225 | try { 226 | projectsDisplayed.push(key); 227 | var featuredStatus = ""; 228 | var featuredShow = "none"; 229 | if (data.featured != "false") { 230 | featuredStatus = "Featured in " + data.featured; 231 | featuredShow = "normal"; 232 | } 233 | var newProject = { 234 | author: data.author, 235 | name: data.name, 236 | timestamp: convertTimestamp(data.timestamp), 237 | desc: data.desc, 238 | link: data.link, 239 | code: data.code, 240 | upvote: data.upvote, 241 | featured: featuredStatus, 242 | featuredShow: featuredShow, 243 | uid: key 244 | } 245 | $("#loadButton").attr("onclick", "loadMoreProjects('" + data.timestamp + "')") 246 | loadShipment(newProject); 247 | } 248 | catch (e) { 249 | console.log("Warning: Unknown error occured. The content is successfully rendered."); 250 | console.log(e); 251 | } 252 | } 253 | 254 | function createProject() { 255 | if (isConnected == true) { 256 | var inputs = ["author", "name", "description", "liveLink", "codeLink", "username"]; 257 | var completed = true; 258 | for (var i = 0; i < inputs.length - 1; i++) { 259 | $("#" + inputs[i]).attr('class', 'input'); 260 | if (!$("#" + inputs[i]).val()) { 261 | $("#" + inputs[i]).addClass('is-danger'); 262 | completed = false; 263 | } 264 | } 265 | if ($("#" + inputs[5]).val()) { 266 | completed = false; 267 | } 268 | if (!checkIfValidURL($("#" + inputs[3]).val())) { 269 | completed = false; 270 | $("#" + inputs[3]).addClass('is-danger'); 271 | } 272 | if (!checkIfValidURL($("#" + inputs[4]).val())) { 273 | completed = false; 274 | $("#" + inputs[4]).addClass('is-danger'); 275 | } 276 | if (completed) { 277 | if (firebase.auth().currentUser != null) { 278 | var ts = getTimeStamp(); 279 | var newProjectRef = projectsRef.push(); 280 | newProjectRef.set({ 281 | author: $("#" + inputs[0]).val(), 282 | name: $("#" + inputs[1]).val(), 283 | timestamp: ts, 284 | desc: $("#" + inputs[2]).val(), 285 | link: $("#" + inputs[3]).val(), 286 | code: $("#" + inputs[4]).val(), 287 | upvote: 0, 288 | flagged: 0, 289 | featured: "false", 290 | uid: firebase.auth().currentUser.uid 291 | }); 292 | 293 | shortLinkForSlack($("#" + inputs[0]).val(), $("#" + inputs[1]).val(), $("#" + inputs[3]).val(), $("#" + inputs[4]).val(), $("#" + inputs[2]).val(), ts, newProjectRef.key); 294 | 295 | var addShippedRef = database.ref("/users/" + firebase.auth().currentUser.uid + "/shipped/" + newProjectRef.key); 296 | var updates = { 297 | name: newProjectRef.key 298 | }; 299 | addShippedRef.update(updates); 300 | } 301 | else { 302 | toastr.error("You are not logged in... Cheater!"); 303 | } 304 | } 305 | else { 306 | toastr.error("Shipping error: Check for fields in red!"); 307 | } 308 | } 309 | else { 310 | //Mingjie work some css magic or something 311 | } 312 | } 313 | 314 | function makeSlackCall(author, name, link, code, desc, ts, uvurl) { 315 | var url = "68747470733a2f2f686f6f6b732e736c61636b2e636f6d2f73657276696365732f54303236364652474d2f42384d5458385a345a2f614e6431654f575a574b6630715644596632524b4b757966"; 316 | 317 | $.ajax({ 318 | data: 'payload=' + JSON.stringify({ 319 | "attachments": [{ 320 | "fallback": "New project from *" + author + "*: " + name + "\nView Project: " + uvurl, 321 | "pretext": "New project from *" + author + "* - click title to upvote!", 322 | "title": name, 323 | "title_link": uvurl, 324 | "text": desc + "\n*Get it*: " + link + "\n*Source*: " + code, 325 | "color": getRandomColor(), 326 | "ts": Math.floor(ts / 1000) 327 | }] 328 | }), 329 | dataType: 'json', 330 | processData: false, 331 | type: 'POST', 332 | url: hts(url), 333 | success: finishShipper() 334 | }); 335 | } 336 | 337 | function getRandomColor() { 338 | var letters = '0123456789ABCDEF'; 339 | var color = '#'; 340 | for (var i = 0; i < 6; i++) { 341 | color += letters[Math.floor(Math.random() * 16)]; 342 | } 343 | return color; 344 | } 345 | 346 | function hts(h) { 347 | var hex = h.toString(); //force conversion 348 | var str = ''; 349 | for (var i = 0; i < hex.length; i += 2) 350 | str += String.fromCharCode(parseInt(hex.substr(i, 2), 16)); 351 | return str; 352 | } 353 | 354 | function checkIfValidURL(value, ssl) { 355 | return value.substring(0, 4) == "http" 356 | } 357 | 358 | function convertTimestamp(id) { 359 | var currentDate = new Date(id); 360 | var hours = currentDate.getHours(); 361 | var minutes = currentDate.getMinutes(); 362 | var dd = currentDate.getDate(); 363 | var mm = monthNames[currentDate.getMonth()] 364 | var yyyy = currentDate.getFullYear(); 365 | var ampm = hours >= 12 ? 'PM' : 'AM'; 366 | hours = hours % 12; 367 | hours = hours ? hours : 12; 368 | minutes = minutes < 10 ? '0' + minutes : minutes; 369 | var strTime = hours + ':' + minutes + ' ' + ampm; 370 | return strTime + " - " + dd + " " + mm + " " + yyyy; 371 | } 372 | 373 | function getTimeStamp() { 374 | var date = Date.now(); 375 | return date; 376 | } 377 | 378 | function startUpVote(key) { 379 | if (firebase.auth().currentUser != null) { 380 | if (upvoteStatus) { 381 | upvoteStatus = false; 382 | checkIfAlreadyUpvoted(firebase.auth().currentUser.uid, key); 383 | } 384 | } 385 | else { 386 | forceLogin(); 387 | } 388 | } 389 | 390 | function unVoteProject(userId, key) { 391 | try { 392 | var tempRef = database.ref("/users/" + userId + "/upVoted/" + key); 393 | tempRef.remove(); 394 | $("#num" + key).text(parseInt($("#num" + key).text()) - 1); 395 | $("#num" + key).removeClass("is-danger"); 396 | $("#num" + key).addClass("is-light"); 397 | updateUpVoteCount(key, "subtract"); 398 | upvoteStatus = true; 399 | } 400 | catch (e) { 401 | toastr.error("This is most likely because you are not logged in, or you are a cheater.", "Error unvoting.") 402 | } 403 | } 404 | 405 | function upVoteProject(userId, key) { 406 | try { 407 | var addUpVoteRef = database.ref("/users/" + userId + "/upVoted/" + key); 408 | var updates = { 409 | name: key 410 | }; 411 | updateUpVoteCount(key, "add"); 412 | $("#num" + key).removeClass("is-light"); 413 | $("#num" + key).addClass("is-danger"); 414 | $("#num" + key).text(parseInt($("#num" + key).text()) + 1); 415 | addUpVoteRef.update(updates); 416 | 417 | upvoteStatus = true; 418 | } 419 | catch (e) { 420 | toastr.error("This is most likely because you are not logged in, or you are a cheater.", "Error upvoting.") 421 | } 422 | } 423 | 424 | function updateUpVoteCount(key, state) { 425 | var updateUpVoteRef = database.ref("/projects/" + key); 426 | updateUpVoteRef.once("value", function (snapshot) { 427 | if (state === "add") { 428 | updateUpVoteRef.update({ upvote: snapshot.val().upvote + 1 }); 429 | } 430 | else { 431 | updateUpVoteRef.update({ upvote: snapshot.val().upvote - 1 }); 432 | } 433 | }); 434 | } 435 | 436 | function checkIfAlreadyUpvoted(userId, key) { 437 | var checkRef = database.ref("/users/" + userId + "/upVoted/"); 438 | var check = true; 439 | checkRef.once('value', function (snapshot) { 440 | if (snapshot.val() === null) { 441 | upVoteProject(userId, key); 442 | } 443 | else { 444 | if (Object.keys(snapshot.val()).indexOf(key) != -1) { 445 | unVoteProject(userId, key); 446 | } 447 | else { 448 | upVoteProject(userId, key); 449 | } 450 | } 451 | }); 452 | } 453 | 454 | function getProp(id) { 455 | var specificRef = database.ref("/projects/" + id) 456 | specificRef.once("value", function (snapshot) { 457 | try { 458 | buildPage(snapshot.val(), id); 459 | } 460 | catch (e) { 461 | toastr.error("Project not found!") 462 | } 463 | }); 464 | } 465 | 466 | function buildPage(data, key) { 467 | displayProjects(data, key); 468 | } 469 | 470 | function addNewUser(userId) { 471 | var newUserRef = database.ref("/users/" + userId) 472 | var updates = {}; 473 | newUserRef.set({ 474 | name: firebase.auth().currentUser.displayName, 475 | upvoted: null, 476 | projects: null 477 | }); 478 | } 479 | 480 | function checkForFirstTime(userId) { 481 | databaseRef.child('users').child(userId).once('value', function (snapshot) { 482 | var exists = (snapshot.val() !== null); 483 | userFirstTimeCallback(userId, exists); 484 | }); 485 | } 486 | 487 | function userFirstTimeCallback(userId, exists) { 488 | if (!exists) { 489 | addNewUser(userId); 490 | } 491 | else { 492 | loadUpVotedProjects(userId); 493 | loadFlaggedProjects(userId); 494 | } 495 | } 496 | 497 | function loadUpVotedProjects(userId) { 498 | databaseRef.child('users').child(userId).child('upVoted').once('value', function (snapshot) { 499 | snapshot.forEach(function (data) { 500 | crossCheckProjects(data.val().name); 501 | }); 502 | }); 503 | } 504 | 505 | function loadFlaggedProjects(userId) { 506 | databaseRef.child('users').child(userId).child('flagged').once('value', function (snapshot) { 507 | snapshot.forEach(function (data) { 508 | crossFlagProjects(data.val().name); 509 | }); 510 | }); 511 | } 512 | 513 | function crossFlagProjects(key) { 514 | if (projectsDisplayed.indexOf(key) != -1) { 515 | $("#project" + key).hide(); 516 | } 517 | } 518 | 519 | function crossCheckProjects(key) { 520 | if (projectsDisplayed.indexOf(key) != -1) { 521 | $("#num" + key).removeClass("is-light"); 522 | $("#num" + key).addClass("is-danger"); 523 | } 524 | } 525 | 526 | function loadMoreProjects() { 527 | queryIr = 5; 528 | requestNextProj(lastProjLoaded); 529 | } 530 | 531 | function requestNextProj(ts) { 532 | if (queryIr > 0) { 533 | try { 534 | query.endAt(ts - 1, "timestamp").limitToLast(1).on('child_added', function (snapshot, prevChildKey) { 535 | displayProjectsDown(snapshot.val(), snapshot.key); 536 | requestNextProj(snapshot.val().timestamp); 537 | queryIr--; 538 | }); 539 | } 540 | catch (e) { 541 | console.log(e); 542 | } 543 | } 544 | lastProjLoaded = ts; 545 | loadUpVotedProjects(firebase.auth().currentUser.uid); 546 | loadFlaggedProjects(firebase.auth().currentUser.uid); 547 | sfired = false; 548 | } 549 | 550 | 551 | function displayProjectsDown(data, key) { 552 | try { 553 | projectsDisplayed.push(key); 554 | var featuredStatus = ""; 555 | var featuredShow = "none"; 556 | if (data.featured != "false") { 557 | featuredStatus = "Featured in " + data.featured; 558 | featuredShow = "normal"; 559 | } 560 | var newProject = { 561 | author: data.author, 562 | name: data.name, 563 | timestamp: convertTimestamp(data.timestamp), 564 | desc: data.desc, 565 | link: data.link, 566 | code: data.code, 567 | upvote: data.upvote, 568 | featured: featuredStatus, 569 | featuredShow: featuredShow, 570 | uid: key 571 | } 572 | $("#loadButton").attr("onclick", "loadMoreProjects('" + data.timestamp + "')") 573 | $("#shipped-placeholder").slideUp("slow"); 574 | $("#shipped").append(template(newProject)); 575 | $(".unlaunch").on("click", closeShipper); 576 | $(".modal-background").on("click", closeShipper); 577 | } 578 | catch (e) { 579 | console.log("Warning: Unknown error occured. The content is successfully rendered."); 580 | console.log(e); 581 | } 582 | } 583 | 584 | function showUpvotedPage() { 585 | 586 | $("#loadButton").hide(); 587 | $("#title-banner").html("Your upvoted collection...") 588 | 589 | projectsDisplayed = []; 590 | $("#shipped").html(""); 591 | var checkRef = database.ref("/users/" + firebase.auth().currentUser.uid + "/upVoted/"); 592 | checkRef.once('value', function (snapshot) { 593 | snapshot.forEach(function (data) { 594 | getProjectsFromKey(data.val()) 595 | }); 596 | }); 597 | 598 | } 599 | 600 | function showShippedPage() { 601 | $("#loadButton").hide(); 602 | $("#title-banner").html("Your shipped projects...") 603 | 604 | projectsDisplayed = []; 605 | $("#shipped").html(""); 606 | var checkRef = database.ref("/users/" + firebase.auth().currentUser.uid + "/shipped/"); 607 | checkRef.once('value', function (snapshot) { 608 | snapshot.forEach(function (data) { 609 | getProjectsFromKey(data.val()) 610 | }); 611 | }); 612 | 613 | } 614 | 615 | function getProjectsFromKey(keys) { 616 | var testRef = database.ref("projects/" + keys.name); 617 | testRef.once("value", function (snapshot) { 618 | displayProjects(snapshot.val(), snapshot.key); 619 | $("#num" + snapshot.key).removeClass("is-light"); 620 | $("#num" + snapshot.key).addClass("is-danger"); 621 | }); 622 | } 623 | 624 | function flagModal(uid) { 625 | $("#flag-modal" + uid).addClass("is-active"); 626 | setTimeout(function () { 627 | $("#confirm-flag-" + uid).removeClass("is-loading"); 628 | $("#confirm-flag-" + uid).attr("disabled", false); 629 | }, 3000); 630 | } 631 | 632 | function startFlag(uid) { 633 | if (firebase.auth().currentUser != null) { 634 | checkIfAlreadyFlagged(firebase.auth().currentUser.uid, uid); 635 | } 636 | else { 637 | forceLogin(); 638 | } 639 | 640 | } 641 | 642 | function flagProj(uid) { 643 | var userId = firebase.auth().currentUser.uid; 644 | try { 645 | var addFlagRef = database.ref("/users/" + userId + "/flagged/" + uid); 646 | var updates = { 647 | name: uid 648 | }; 649 | updateFlagCount(uid); 650 | $("#project" + uid).hide(); 651 | addFlagRef.update(updates); 652 | 653 | closeShipper(); 654 | } 655 | catch (e) { 656 | console.log(e); 657 | toastr.error("This is most likely because you are not logged in, or you are a cheater.", "Error upvoting.") 658 | } 659 | 660 | } 661 | 662 | function checkIfAlreadyFlagged(userId, key) { 663 | var checkRef = database.ref("/users/" + userId + "/flagged/"); 664 | var check = true; 665 | checkRef.once('value', function (snapshot) { 666 | if (snapshot.val() === null) { 667 | flagModal(key); 668 | } 669 | else { 670 | if (Object.keys(snapshot.val()).indexOf(key) != -1) { 671 | toastr.error("You have already flagged this post! You cannot unflag it.") 672 | } 673 | else { 674 | flagModal(key); 675 | } 676 | } 677 | }); 678 | } 679 | 680 | function updateFlagCount(key) { 681 | var updateFlagRef = database.ref("/projects/" + key); 682 | updateFlagRef.once("value", function (snapshot) { 683 | updateFlagRef.update({ flagged: snapshot.val().flagged + 1 }); 684 | }); 685 | } 686 | -------------------------------------------------------------------------------- /asset/js/config.dev.js: -------------------------------------------------------------------------------- 1 | // Initialize Firebase - DEV BASE 2 | var config = { 3 | apiKey: "AIzaSyDxvQeq7iqqfh2ZZeJZMWyLxXCX0KPMoBs", 4 | authDomain: "shipit-alpha.firebaseapp.com", 5 | databaseURL: "https://shipit-alpha.firebaseio.com", 6 | projectId: "shipit-alpha", 7 | storageBucket: "shipit-alpha.appspot.com", 8 | messagingSenderId: "740447864312" 9 | }; -------------------------------------------------------------------------------- /asset/js/config.prod.js: -------------------------------------------------------------------------------- 1 | // Initialize Firebase - PRODUCTION BASE 2 | var config = { 3 | apiKey: "AIzaSyD-IT1RWXi-7bMSjtTsPmpaTD2SXadFxC0", 4 | authDomain: "shipit-7427d.firebaseapp.com", 5 | databaseURL: "https://shipit-7427d.firebaseio.com", 6 | projectId: "shipit-7427d", 7 | storageBucket: "shipit-7427d.appspot.com", 8 | messagingSenderId: "601650858338" 9 | }; -------------------------------------------------------------------------------- /asset/js/newShip.js: -------------------------------------------------------------------------------- 1 | toastr.options.showMethod = 'slideDown'; 2 | toastr.options.hideMethod = 'slideUp'; 3 | toastr.options.closeMethod = 'slideUp'; 4 | toastr.options.showEasing = 'swing'; 5 | toastr.options.hideEasing = 'linear'; 6 | toastr.options.closeEasing = 'linear'; 7 | 8 | toastr.options.closeButton = true; 9 | 10 | $("#logged-in-user").on("click", triggerAccountMenu); 11 | 12 | function triggerAccountMenu() { 13 | $("#account-menu").slideToggle(100); 14 | } 15 | 16 | window.onload = function() { 17 | console.log(firebase.auth().currentUser); 18 | } 19 | 20 | function closeShipper() { 21 | $(".modal").removeClass("is-active"); 22 | } 23 | 24 | function finishShipper() { 25 | window.location = "../"; 26 | } 27 | 28 | $.get("https://api.github.com/repos/mj66/shipit-frontend/commits", function (data, status) { 29 | $("#commit-id").html(data[0].sha); 30 | $("#commit-id").attr("href", data[0].html_url); 31 | $("#commit-id").attr("title", data[0].commit.message); 32 | }); 33 | 34 | function toTop() { 35 | $("html, body").animate({ scrollTop: 0 }, "slow"); 36 | return false; 37 | } 38 | -------------------------------------------------------------------------------- /asset/js/render.js: -------------------------------------------------------------------------------- 1 | var shipment = $("#shipment-templ").html(); 2 | var template = Handlebars.compile(shipment); 3 | 4 | var featuredShipment = $("#featured-templ").html(); 5 | var featured = Handlebars.compile(featuredShipment); 6 | 7 | toastr.options.showMethod = 'slideDown'; 8 | toastr.options.hideMethod = 'slideUp'; 9 | toastr.options.closeMethod = 'slideUp'; 10 | toastr.options.showEasing = 'swing'; 11 | toastr.options.hideEasing = 'linear'; 12 | toastr.options.closeEasing = 'linear'; 13 | 14 | toastr.options.closeButton = true; 15 | 16 | function loadShipment(id) { 17 | $("#shipped-placeholder").slideUp("slow"); 18 | $("#shipped").prepend(template(id)); 19 | 20 | $(".unlaunch").on("click", closeShipper); 21 | $(".modal-background").on("click", closeShipper); 22 | 23 | } 24 | 25 | function loadFeatured(id) { 26 | $("#shipped-placeholder").slideUp("slow"); 27 | $("#shipped").prepend(featured(id)); 28 | 29 | $(".unlaunch").on("click", closeShipper); 30 | $(".modal-background").on("click", closeShipper); 31 | } 32 | 33 | $("#launch").on("click", openShipper); 34 | $("#logged-in-user").on("click", triggerAccountMenu); 35 | 36 | function triggerAccountMenu() { 37 | $("#account-menu").slideToggle(100); 38 | } 39 | 40 | function openShipper() { 41 | console.log(firebase.auth().currentUser); 42 | if (firebase.auth().currentUser != null) { 43 | window.location = "new/"; 44 | } else { 45 | forceLogin(); 46 | } 47 | } 48 | 49 | function closeShipper() { 50 | $(".modal").removeClass("is-active"); 51 | } 52 | 53 | function forceLogin() { 54 | $("#login-modal").addClass("is-active"); 55 | } 56 | 57 | function shareShipment(uid) { 58 | getSL(uid); 59 | $("#share-modal" + uid).addClass("is-active"); 60 | } 61 | 62 | $.get("https://api.github.com/repos/mj66/shipit-frontend/commits", function (data, status) { 63 | $("#commit-id").html(data[0].sha); 64 | $("#commit-id").attr("href", data[0].html_url); 65 | $("#commit-id").attr("title", data[0].commit.message); 66 | }); 67 | 68 | function toTop() { 69 | $("html, body").animate({ scrollTop: 0 }, "slow"); 70 | return false; 71 | } -------------------------------------------------------------------------------- /asset/sass/base/_font.scss: -------------------------------------------------------------------------------- 1 | /* Averta */ 2 | @font-face { 3 | font-family: Averta; 4 | font-style: normal; 5 | font-weight: normal; 6 | src: url("../fonts/averta-regular.woff2") format("woff2"), url("../fonts/averta-regular.woff") format("woff"); 7 | unicode-range: U+0000-F8FE, U+F900-FFFF; 8 | } 9 | 10 | @font-face { 11 | font-family: Averta; 12 | font-style: normal; 13 | font-weight: bold; 14 | src: url("../fonts/averta-bold.woff2") format("woff2"), url("../fonts/averta-bold.woff") format("woff"); 15 | unicode-range: U+0000-F8FE, U+F900-FFFF; 16 | } -------------------------------------------------------------------------------- /asset/sass/main.scss: -------------------------------------------------------------------------------- 1 | // Font Awesome 2 | @import "../../node_modules/font-awesome/scss/font-awesome.scss"; 3 | 4 | 5 | //Normalize 6 | @import "../../node_modules/normalize.css/normalize.css"; 7 | 8 | //Bulma 9 | @import "../../node_modules/bulma/sass/utilities/functions"; 10 | //@import "../../node_modules/bulma/sass/utilities/initial-variables"; 11 | 12 | //Toastr 13 | @import "../../node_modules/toastr/toastr"; 14 | 15 | // Variables 16 | $light: #ffffff; 17 | $black: #384046; 18 | $grey: #dde1e4; 19 | $grey-light: #f9f9fa; 20 | $red: #e42d42; 21 | 22 | $family-sans-serif: Averta, -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", sans-serif; 23 | 24 | $primary: $red; 25 | $family-primary: Averta, -apple-system, BlinkMacSystemFont, "Segoe UI", Roboto, "Helvetica Neue", sans-serif; 26 | 27 | $body-color: $black; 28 | 29 | $link: $primary; 30 | $link-hover: $primary; 31 | 32 | // Bulma 33 | @import "../../node_modules/bulma/bulma"; 34 | 35 | //Shipit 36 | @import "base/font"; -------------------------------------------------------------------------------- /asset/sass/style.scss: -------------------------------------------------------------------------------- 1 | body, html, nav { 2 | background: linear-gradient(90deg, #ce293c 0%, #e42d42 50%, #eb9763 100%); 3 | } 4 | 5 | #main { 6 | margin-top: 3.25rem; 7 | background-color: #FFFFFF; 8 | } 9 | 10 | main { 11 | transition: opacity .5s ease-out; 12 | -moz-transition: opacity .5s ease-out; 13 | -webkit-transition: opacity .5s ease-out; 14 | -o-transition: opacity .5s ease-out; 15 | } 16 | 17 | .shipit { 18 | color: #E42D40 !important; 19 | } 20 | 21 | .shipped .container { 22 | padding: 5px; 23 | margin-top: 10px; 24 | } 25 | 26 | a { 27 | color: #E42D40; 28 | -o-transition: all .15s ease-in-out; 29 | -ms-transition: all .15s ease-in-out; 30 | -moz-transition: all .15s ease-in-out; 31 | -webkit-transition: all .15s ease-in-out; 32 | transition: all .15s ease-in-out; 33 | &:hover { 34 | color: #921D29; 35 | } 36 | } 37 | 38 | .shipment { 39 | .subtitle:not(:last-child), .title:not(:last-child) { 40 | margin-bottom: 0; 41 | } 42 | } 43 | 44 | .banner .hero-body { 45 | padding: 0.75em; 46 | } 47 | 48 | .footer { 49 | margin-top: 20px; 50 | padding: 3rem 2rem 3rem; 51 | } 52 | 53 | .hero.is-danger { 54 | background: linear-gradient(90deg, #ce293c 0%, #e42d42 50%, #eb9763 100%); 55 | } 56 | 57 | .button.is-danger { 58 | background-color: #E42D40; 59 | } 60 | 61 | .navbar { 62 | .button { 63 | box-shadow: none; 64 | } 65 | #nav-name, #nav-name:hover { 66 | color: #ffffff; 67 | background-color: transparent; 68 | } 69 | .button.is-light { 70 | border-color: transparent !important; 71 | } 72 | position: fixed; 73 | background: linear-gradient(90deg, #ce293c 0%, #e42d42 50%, #eb9763 100%); 74 | /* Set the navbar to fixed position */ 75 | top: 0; 76 | /* Position the navbar at the top of the page */ 77 | width: 100%; 78 | /* Full width */ 79 | z-index: 2; 80 | } 81 | 82 | a.navbar-item { 83 | color: #000; 84 | padding: .5rem .5rem; 85 | } 86 | 87 | .navbar-brand { 88 | padding-left: .5rem; 89 | } 90 | 91 | #gh-login, #gh-logout { 92 | text-shadow: none; 93 | } 94 | 95 | a.card-footer-item.is-danger { 96 | border-style: solid; 97 | border-width: 1px; 98 | border-color: #E42D40; 99 | } 100 | 101 | .tag.is-danger { 102 | background-color: #E42D40 !important; 103 | } 104 | 105 | .wabble { 106 | border-radius: 4px; 107 | -webkit-transition: all 0.3s cubic-bezier(0.165, 0.84, 0.44, 1); 108 | transition: all 0.3s cubic-bezier(0.165, 0.84, 0.44, 1); 109 | &::after { 110 | z-index: -1; 111 | opacity: 0; 112 | -webkit-transition: all 0.3s cubic-bezier(0.165, 0.84, 0.44, 1); 113 | transition: all 0.3s cubic-bezier(0.165, 0.84, 0.44, 1); 114 | } 115 | &:hover { 116 | -webkit-transform: scale(1.03, 1.03); 117 | transform: scale(1.03, 1.03); 118 | } 119 | &:active { 120 | -webkit-transform: scale(1, 1); 121 | transform: scale(1, 1); 122 | } 123 | &:hover::after { 124 | opacity: 1; 125 | } 126 | } 127 | 128 | #useravatar { 129 | width: 1.75rem; 130 | height: 1.75rem; 131 | border-radius: 50%; 132 | } 133 | 134 | @media screen and (min-width: 1000px) { 135 | .navbar-item.has-dropdown { 136 | -ms-flex-align: none; 137 | } 138 | } 139 | 140 | #logged-in-user { 141 | cursor: pointer; 142 | } 143 | 144 | .unlaunch.button.is-link { 145 | text-decoration: none; 146 | margin-top: 5px; 147 | margin-right: 5px; 148 | &:hover, &:active { 149 | background-color: #ffffff; 150 | color: #e42d42; 151 | } 152 | } 153 | 154 | #time-travel { 155 | cursor: default; 156 | } 157 | 158 | @keyframes spinner { 159 | to { 160 | transform: rotate(360deg); 161 | } 162 | } 163 | 164 | 165 | .spinner:before { 166 | content: ''; 167 | box-sizing: border-box; 168 | position: absolute; 169 | top: 50%; 170 | left: 50%; 171 | width: 45px; 172 | height: 45px; 173 | margin-top: -10px; 174 | margin-left: -10px; 175 | border-radius: 50%; 176 | border: 2px solid transparent; 177 | border-top-color: #E42D40; 178 | border-bottom-color: #E42D40; 179 | animation: spinner .8s ease infinite; 180 | } 181 | 182 | #shipped-placeholder { 183 | height: 45vh; 184 | } 185 | 186 | .navbar-dropdown { 187 | background-color: #fff !important; 188 | border-bottom-left-radius: 4px; 189 | border-bottom-right-radius: 4px; 190 | border-top: 1px solid #dbdbdb; 191 | -webkit-box-shadow: 0 8px 8px rgba(10, 10, 10, 0.1); 192 | box-shadow: 0 8px 8px rgba(10, 10, 10, 0.1); 193 | display: none; 194 | font-size: .875rem; 195 | left: 0; 196 | min-width: 100%; 197 | position: absolute; 198 | top: 100%; 199 | z-index: 20; 200 | } 201 | 202 | #account-button { 203 | position: fixed; 204 | right: 0; 205 | } 206 | 207 | .card-header-icon:hover, .card-footer-item:hover { 208 | background-color: #E42D40; 209 | color: #fff; 210 | } 211 | 212 | .card-header-icon { 213 | background-color: #fff; 214 | color: #E42D40; 215 | } 216 | 217 | .hero.is-small .hero-body { 218 | margin-bottom: 25px; 219 | } 220 | 221 | .featured-project .card { 222 | -moz-box-shadow: 0 0 10px #e42d42; 223 | -webkit-box-shadow: 0 0 10px #e42d42; 224 | box-shadow: 0px 0px 10px #e42d42; 225 | } 226 | 227 | /*#featured { 228 | 229 | .card .card-header{ 230 | background: linear-gradient(90deg, #ce293c 0%, #e42d42 50%, #eb9763 100%); 231 | 232 | p.card-header-title { 233 | color: #fff; 234 | 235 | small { 236 | color: #fcfcfc; 237 | } 238 | } 239 | 240 | } 241 | 242 | }*/ 243 | 244 | .gradient { 245 | background-image: linear-gradient(90deg, #ce293c 0%, #e42d42 50%, #eb9763 100%); 246 | color: #fff!important; 247 | p{ 248 | color: #fff; 249 | 250 | small { 251 | color: #fefefe; 252 | font-weight: normal; 253 | } 254 | } 255 | 256 | } -------------------------------------------------------------------------------- /gulpfile.js: -------------------------------------------------------------------------------- 1 | const gulp = require("gulp"); 2 | const autoPrefixer = require("gulp-autoprefixer"); 3 | const cleanCSS = require("gulp-clean-css"); 4 | const concat = require("gulp-concat"); 5 | const sass = require("gulp-sass"); 6 | const pump = require("pump"); 7 | 8 | // Change to another module with ES6 support 9 | const composer = require("gulp-uglify/composer"); 10 | const uglify = composer(require("uglify-es"), console); 11 | 12 | const SASS_PATHS = [ 13 | "asset/sass/**/*.scss" 14 | ]; 15 | 16 | gulp.task("default", ["watch"]); 17 | 18 | gulp.task("build", ["build-css"]); 19 | 20 | gulp.task("build-css", cb => { 21 | pump([ 22 | gulp.src(SASS_PATHS), 23 | sass(), 24 | autoPrefixer(), 25 | cleanCSS({ 26 | compatibility: "ie8", 27 | rebase: false 28 | }), 29 | concat("shipit.min.css"), 30 | gulp.dest("asset/dist/") 31 | ], cb); 32 | }); 33 | 34 | gulp.task("watch", ["watch-css"]); 35 | 36 | gulp.task("watch-css", () => gulp.watch(SASS_PATHS, ["build-css"])); 37 | -------------------------------------------------------------------------------- /icons/apple-touch-icon-114x114.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/apple-touch-icon-114x114.png -------------------------------------------------------------------------------- /icons/apple-touch-icon-120x120.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/apple-touch-icon-120x120.png -------------------------------------------------------------------------------- /icons/apple-touch-icon-144x144.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/apple-touch-icon-144x144.png -------------------------------------------------------------------------------- /icons/apple-touch-icon-152x152.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/apple-touch-icon-152x152.png -------------------------------------------------------------------------------- /icons/apple-touch-icon-57x57.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/apple-touch-icon-57x57.png -------------------------------------------------------------------------------- /icons/apple-touch-icon-60x60.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/apple-touch-icon-60x60.png -------------------------------------------------------------------------------- /icons/apple-touch-icon-72x72.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/apple-touch-icon-72x72.png -------------------------------------------------------------------------------- /icons/apple-touch-icon-76x76.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/apple-touch-icon-76x76.png -------------------------------------------------------------------------------- /icons/code.txt: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /icons/favicon-128.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/favicon-128.png -------------------------------------------------------------------------------- /icons/favicon-16x16.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/favicon-16x16.png -------------------------------------------------------------------------------- /icons/favicon-196x196.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/favicon-196x196.png -------------------------------------------------------------------------------- /icons/favicon-32x32.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/favicon-32x32.png -------------------------------------------------------------------------------- /icons/favicon-96x96.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/favicon-96x96.png -------------------------------------------------------------------------------- /icons/favicon.ico: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/favicon.ico -------------------------------------------------------------------------------- /icons/mstile-144x144.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/mstile-144x144.png -------------------------------------------------------------------------------- /icons/mstile-150x150.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/mstile-150x150.png -------------------------------------------------------------------------------- /icons/mstile-310x150.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/mstile-310x150.png -------------------------------------------------------------------------------- /icons/mstile-310x310.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/mstile-310x310.png -------------------------------------------------------------------------------- /icons/mstile-70x70.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/hackclub/shipit/a925b6584260dc01a882aff7dd383bbea74e43a9/icons/mstile-70x70.png -------------------------------------------------------------------------------- /index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | Hack Club Shipit! 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 51 | 52 | 53 | 54 | 55 | 56 |
57 | 89 | 90 |
91 | 92 |
93 |
94 |
95 |

96 | See what other hackers like you are building. 97 |

98 |

99 | Hack Club members learn through the process of making. Join the maker's squad! 100 |

101 |
102 |
103 | 104 |  Ship My Project 105 |
106 |
107 | 108 | 109 | 144 | 145 |
146 |
147 |
148 |
149 |
150 |
151 | 152 | 153 | 236 | 237 |
238 | 239 | 325 |
326 | 327 | 332 |
333 | 334 | 355 | 356 | 357 |
358 |
359 | 360 | 361 | 362 | 363 | 364 | 365 | 366 | 367 | 368 | 369 | 370 | 371 | 372 | 373 | 374 | 375 | -------------------------------------------------------------------------------- /new/index.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | Hack Club Shipit! 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 51 | 52 | 53 | 54 | 55 | 56 |
57 | 83 | 84 |
85 | 86 | 115 | 116 | 117 |
118 |
119 |
120 |

121 | Start shipping your new project! 122 |

123 |

124 | Launching your project starts here, and it's as easy as 1, 2, 3. 125 |

126 |
127 |
128 |
129 | 130 |
131 |
132 |
133 |

Check out the Shipit Community Guidelines before you post to get the most audiences and prevent getting banned!

134 |
135 | 136 |

137 | 138 |

139 |
140 |
141 | 142 |

143 | 144 |

145 |
146 |
147 | 148 |

149 | 150 |

151 |
152 |
153 | 154 |

155 | 156 |

157 |
158 |
159 | 160 |

161 | 162 |

163 |
164 | 170 |

171 | 172 |

173 |
174 |
175 |
176 | 177 | 178 | 193 | 194 | 195 |
196 |
197 | 198 | 199 | 200 | 201 | 202 | 203 | 204 | 205 | 206 | 207 | 208 | 209 | 210 | 211 | 212 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "shipit", 3 | "version": "1.0.0", 4 | "description": "Shipping your project to the Hack Club community.", 5 | "main": "index.html", 6 | "scripts": { 7 | "build": "gulp build", 8 | "test": "echo \"Error: no test specified\" && exit 1" 9 | }, 10 | "repository": { 11 | "type": "git", 12 | "url": "git+https://github.com/hackclub/shipit.git" 13 | }, 14 | "keywords": [ 15 | "hackclub" 16 | ], 17 | "author": "Mingjie Jiang (https://mingjie.info)", 18 | "license": "UNLICENSED", 19 | "bugs": { 20 | "url": "https://github.com/hackclub/shipit/issues" 21 | }, 22 | "homepage": "https://github.com/hackclub/shipit#readme", 23 | "dependencies": { 24 | "bulma": "^0.6.1", 25 | "bulma-slider": "^0.1.0", 26 | "bulma-switch": "^0.1.2", 27 | "font-awesome": "^4.7.0", 28 | "fuse.js": "^3.2.0", 29 | "geolib": "^2.0.24", 30 | "jquery": "^3.2.1", 31 | "toastr": "^2.1.4", 32 | "normalize.css": "^7.0.0" 33 | }, 34 | "devDependencies": { 35 | "gulp": "^3.9.1", 36 | "gulp-autoprefixer": "^4.0.0", 37 | "gulp-clean-css": "^3.9.0", 38 | "gulp-concat": "^2.6.1", 39 | "gulp-imagemin": "^4.0.0", 40 | "gulp-sass": "^3.1.0", 41 | "gulp-uglify": "^3.0.0", 42 | "pump": "^2.0.0", 43 | "uglify-es": "^3.2.2" 44 | } 45 | } 46 | --------------------------------------------------------------------------------