mirror of
https://github.com/dilllxd/gitfolio.git
synced 2024-08-14 22:28:09 +00:00
Setting line endings to unix-style (#95)
* Add gitattributes settings to LF * TY @Pliavi * Converting all CRLF to LF
This commit is contained in:
parent
0e90c885d1
commit
1de7fd23ef
24 changed files with 4560 additions and 4555 deletions
5
.gitattributes
vendored
Normal file
5
.gitattributes
vendored
Normal file
|
@ -0,0 +1,5 @@
|
|||
# Set the default behavior, in case people don't have core.autocrlf set
|
||||
* text=auto
|
||||
|
||||
# Require Unix line endings
|
||||
* text eol=lf
|
|
@ -1,76 +1,76 @@
|
|||
# Contributor Covenant Code of Conduct
|
||||
|
||||
## Our Pledge
|
||||
|
||||
In the interest of fostering an open and welcoming environment, we as
|
||||
contributors and maintainers pledge to making participation in our project and
|
||||
our community a harassment-free experience for everyone, regardless of age, body
|
||||
size, disability, ethnicity, sex characteristics, gender identity and expression,
|
||||
level of experience, education, socio-economic status, nationality, personal
|
||||
appearance, race, religion, or sexual identity and orientation.
|
||||
|
||||
## Our Standards
|
||||
|
||||
Examples of behavior that contributes to creating a positive environment
|
||||
include:
|
||||
|
||||
- Using welcoming and inclusive language
|
||||
- Being respectful of differing viewpoints and experiences
|
||||
- Gracefully accepting constructive criticism
|
||||
- Focusing on what is best for the community
|
||||
- Showing empathy towards other community members
|
||||
|
||||
Examples of unacceptable behavior by participants include:
|
||||
|
||||
- The use of sexualized language or imagery and unwelcome sexual attention or
|
||||
advances
|
||||
- Trolling, insulting/derogatory comments, and personal or political attacks
|
||||
- Public or private harassment
|
||||
- Publishing others' private information, such as a physical or electronic
|
||||
address, without explicit permission
|
||||
- Other conduct which could reasonably be considered inappropriate in a
|
||||
professional setting
|
||||
|
||||
## Our Responsibilities
|
||||
|
||||
Project maintainers are responsible for clarifying the standards of acceptable
|
||||
behavior and are expected to take appropriate and fair corrective action in
|
||||
response to any instances of unacceptable behavior.
|
||||
|
||||
Project maintainers have the right and responsibility to remove, edit, or
|
||||
reject comments, commits, code, wiki edits, issues, and other contributions
|
||||
that are not aligned to this Code of Conduct, or to ban temporarily or
|
||||
permanently any contributor for other behaviors that they deem inappropriate,
|
||||
threatening, offensive, or harmful.
|
||||
|
||||
## Scope
|
||||
|
||||
This Code of Conduct applies both within project spaces and in public spaces
|
||||
when an individual is representing the project or its community. Examples of
|
||||
representing a project or community include using an official project e-mail
|
||||
address, posting via an official social media account, or acting as an appointed
|
||||
representative at an online or offline event. Representation of a project may be
|
||||
further defined and clarified by project maintainers.
|
||||
|
||||
## Enforcement
|
||||
|
||||
Instances of abusive, harassing, or otherwise unacceptable behavior may be
|
||||
reported by contacting the project team at imfunny@wybemf.com. All
|
||||
complaints will be reviewed and investigated and will result in a response that
|
||||
is deemed necessary and appropriate to the circumstances. The project team is
|
||||
obligated to maintain confidentiality with regard to the reporter of an incident.
|
||||
Further details of specific enforcement policies may be posted separately.
|
||||
|
||||
Project maintainers who do not follow or enforce the Code of Conduct in good
|
||||
faith may face temporary or permanent repercussions as determined by other
|
||||
members of the project's leadership.
|
||||
|
||||
## Attribution
|
||||
|
||||
This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4,
|
||||
available at https://www.contributor-covenant.org/version/1/4/code-of-conduct.html
|
||||
|
||||
[homepage]: https://www.contributor-covenant.org
|
||||
|
||||
For answers to common questions about this code of conduct, see
|
||||
https://www.contributor-covenant.org/faq
|
||||
# Contributor Covenant Code of Conduct
|
||||
|
||||
## Our Pledge
|
||||
|
||||
In the interest of fostering an open and welcoming environment, we as
|
||||
contributors and maintainers pledge to making participation in our project and
|
||||
our community a harassment-free experience for everyone, regardless of age, body
|
||||
size, disability, ethnicity, sex characteristics, gender identity and expression,
|
||||
level of experience, education, socio-economic status, nationality, personal
|
||||
appearance, race, religion, or sexual identity and orientation.
|
||||
|
||||
## Our Standards
|
||||
|
||||
Examples of behavior that contributes to creating a positive environment
|
||||
include:
|
||||
|
||||
- Using welcoming and inclusive language
|
||||
- Being respectful of differing viewpoints and experiences
|
||||
- Gracefully accepting constructive criticism
|
||||
- Focusing on what is best for the community
|
||||
- Showing empathy towards other community members
|
||||
|
||||
Examples of unacceptable behavior by participants include:
|
||||
|
||||
- The use of sexualized language or imagery and unwelcome sexual attention or
|
||||
advances
|
||||
- Trolling, insulting/derogatory comments, and personal or political attacks
|
||||
- Public or private harassment
|
||||
- Publishing others' private information, such as a physical or electronic
|
||||
address, without explicit permission
|
||||
- Other conduct which could reasonably be considered inappropriate in a
|
||||
professional setting
|
||||
|
||||
## Our Responsibilities
|
||||
|
||||
Project maintainers are responsible for clarifying the standards of acceptable
|
||||
behavior and are expected to take appropriate and fair corrective action in
|
||||
response to any instances of unacceptable behavior.
|
||||
|
||||
Project maintainers have the right and responsibility to remove, edit, or
|
||||
reject comments, commits, code, wiki edits, issues, and other contributions
|
||||
that are not aligned to this Code of Conduct, or to ban temporarily or
|
||||
permanently any contributor for other behaviors that they deem inappropriate,
|
||||
threatening, offensive, or harmful.
|
||||
|
||||
## Scope
|
||||
|
||||
This Code of Conduct applies both within project spaces and in public spaces
|
||||
when an individual is representing the project or its community. Examples of
|
||||
representing a project or community include using an official project e-mail
|
||||
address, posting via an official social media account, or acting as an appointed
|
||||
representative at an online or offline event. Representation of a project may be
|
||||
further defined and clarified by project maintainers.
|
||||
|
||||
## Enforcement
|
||||
|
||||
Instances of abusive, harassing, or otherwise unacceptable behavior may be
|
||||
reported by contacting the project team at imfunny@wybemf.com. All
|
||||
complaints will be reviewed and investigated and will result in a response that
|
||||
is deemed necessary and appropriate to the circumstances. The project team is
|
||||
obligated to maintain confidentiality with regard to the reporter of an incident.
|
||||
Further details of specific enforcement policies may be posted separately.
|
||||
|
||||
Project maintainers who do not follow or enforce the Code of Conduct in good
|
||||
faith may face temporary or permanent repercussions as determined by other
|
||||
members of the project's leadership.
|
||||
|
||||
## Attribution
|
||||
|
||||
This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 1.4,
|
||||
available at https://www.contributor-covenant.org/version/1/4/code-of-conduct.html
|
||||
|
||||
[homepage]: https://www.contributor-covenant.org
|
||||
|
||||
For answers to common questions about this code of conduct, see
|
||||
https://www.contributor-covenant.org/faq
|
||||
|
|
322
README.md
322
README.md
|
@ -1,161 +1,161 @@
|
|||
<img src="https://i.imgur.com/eA6clZr.png">
|
||||
|
||||
# Gitfolio
|
||||
[![Tweet](https://img.shields.io/twitter/url/https/shields.io.svg?style=social)](https://twitter.com/intent/tweet?text=personal%20website%20and%20a%20blog%20for%20every%20github%20user%20@imfunnieee%20&url=https://github.com/imfunniee/gitfolio) ![GitHub release](https://img.shields.io/github/release/imfunniee/gitfolio.svg?style=popout-square) ![npm](https://img.shields.io/npm/dm/gitfolio.svg?style=popout-square) ![GitHub top language](https://img.shields.io/github/languages/top/imfunniee/gitfolio.svg?style=popout-square) ![GitHub last commit](https://img.shields.io/github/last-commit/imfunniee/gitfolio.svg?style=popout-square) ![GitHub](https://img.shields.io/github/license/imfunniee/gitfolio.svg?style=popout-square) [![code style: prettier](https://img.shields.io/badge/code_style-prettier-ff69b4.svg?style=flat-square)](https://github.com/prettier/prettier)
|
||||
|
||||
### personal website + blog for every github user
|
||||
|
||||
Gitfolio will help you get started with a portfolio website where you could showcase your work + a blog that will help you spread your ideas into real world.
|
||||
|
||||
Check out this [live demo](https://imfunniee.github.io/gitfolio/) to see gitfolio in action.
|
||||
|
||||
# Getting Started
|
||||
|
||||
### Let's Install
|
||||
|
||||
Install gitfolio
|
||||
|
||||
```sh
|
||||
npm i gitfolio -g
|
||||
```
|
||||
|
||||
### Let's Build
|
||||
|
||||
Using the UI
|
||||
|
||||
```sh
|
||||
$ gitfolio ui
|
||||
```
|
||||
|
||||
> Tip: You can use ui to create new blogs and for updating your folio too.
|
||||
|
||||
or
|
||||
|
||||
```sh
|
||||
gitfolio build <username>
|
||||
```
|
||||
|
||||
`<username>` is your username on github. This will build your website using your GitHub username and put it in the `/dist` folder.
|
||||
|
||||
To run your website use `run` command, Default port is 3000
|
||||
|
||||
```sh
|
||||
gitfolio run -p [port]
|
||||
```
|
||||
|
||||
🎉 Congrats, you just made yourself a personal website!
|
||||
|
||||
### Let's Customize
|
||||
|
||||
#### Forks
|
||||
|
||||
To include forks on your personal website just provide `-f` or `--fork` argument while building
|
||||
|
||||
```sh
|
||||
$ gitfolio build <username> -f
|
||||
```
|
||||
|
||||
#### Sorting Repos
|
||||
|
||||
To sort repos provide `--sort [sortBy]` argument while building. Where `[sortBy]` can be `star`, `created`, `updated`, `pushed`,`full_name`. Default: `created`
|
||||
|
||||
```sh
|
||||
$ gitfolio build <username> --sort star
|
||||
```
|
||||
|
||||
#### Ordering Repos
|
||||
|
||||
To order the sorted repos provide `--order [orderBy]` argument while building. Where `[orderBy]` can be `asc` or `desc`. Default: `asc`
|
||||
|
||||
```sh
|
||||
$ gitfolio build <username> --sort star --order desc
|
||||
```
|
||||
|
||||
#### Customize Themes
|
||||
|
||||
Themes are specified using the `--theme [theme-name]` flag when running the `build` command. The available themes are
|
||||
|
||||
- `light`
|
||||
- `dark`
|
||||
|
||||
> TODO: Add more themes
|
||||
|
||||
For example, the following command will build the website with the dark theme
|
||||
|
||||
```sh
|
||||
$ gitfolio build <username> --theme dark
|
||||
```
|
||||
|
||||
#### Customize background image
|
||||
|
||||
To customize the background image just provide `--background [url]` argument while building
|
||||
|
||||
```sh
|
||||
$ gitfolio build <username> --background https://images.unsplash.com/photo-1557277770-baf0ca74f908?w=1634
|
||||
```
|
||||
|
||||
You could also add in your custom CSS inside `index.css` to give it a more personal feel.
|
||||
|
||||
#### Add Social Media links on your profile
|
||||
|
||||
Twitter, LinkedIn, Medium & Dribbble links to your profile while building
|
||||
|
||||
```sh
|
||||
gitfolio build <username> --twitter <twitter_username> --linkedin <linkedin_username> --medium <medium_username> --dribbble <dribbble_username>
|
||||
```
|
||||
|
||||
### Let's Publish
|
||||
|
||||
Head over to GitHub and create a new repository named `username.github.io`, where username is your username. Push the files inside`/dist` folder to repo you just created.
|
||||
|
||||
Go To `username.github.io` your site should be up!!
|
||||
|
||||
### Updating
|
||||
|
||||
To update your info, simply run
|
||||
|
||||
```sh
|
||||
$ gitfolio update
|
||||
```
|
||||
|
||||
or use the `Update` options in gitfolio's UI
|
||||
|
||||
This will update your info and your repository info.
|
||||
|
||||
To Update background or theme you need to run `build` command again.
|
||||
|
||||
### Add a Blog
|
||||
|
||||
To add your first blog use the UI.
|
||||
|
||||
```sh
|
||||
$ gitfolio ui
|
||||
```
|
||||
|
||||
This will open up a UI page and you can click on `New Blog` to create a new blog. Once you are done writing your blog you can hit the `Create Blog`.
|
||||
|
||||
This will create a blog inside `./dist/blog` folder.
|
||||
|
||||
Look for success or error in your terminal.
|
||||
|
||||
This also adds content to `blog.json` file. This file helps in showcasing your blogs on your personal website as [cards](https://imfunniee.github.io/gitfolio/#blog_section). You could customize the JSON object that corresponds your current blog.
|
||||
|
||||
Blog Demo? [here](https://imfunniee.github.io/gitfolio/blog/my-first-post/)
|
||||
|
||||
Blog's default JSON Format
|
||||
|
||||
```
|
||||
{
|
||||
"url_title": "my-first-blog", // the title you provide while creating a new blog, this appears in url
|
||||
"title": "Lorem ipsum dolor sit amet", // main title of blog
|
||||
"sub_title": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.", // sub-title of blog
|
||||
"top_image": "https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1450", // main image of blog
|
||||
"visible": true // don't worry about this
|
||||
}
|
||||
```
|
||||
|
||||
### Follow me on twitter for more updates [@imfunnieee](https://twitter.com/imfunnieee)
|
||||
|
||||
### License
|
||||
|
||||
![GitHub](https://img.shields.io/github/license/imfunniee/gitfolio.svg?style=popout-square)
|
||||
<img src="https://i.imgur.com/eA6clZr.png">
|
||||
|
||||
# Gitfolio
|
||||
[![Tweet](https://img.shields.io/twitter/url/https/shields.io.svg?style=social)](https://twitter.com/intent/tweet?text=personal%20website%20and%20a%20blog%20for%20every%20github%20user%20@imfunnieee%20&url=https://github.com/imfunniee/gitfolio) ![GitHub release](https://img.shields.io/github/release/imfunniee/gitfolio.svg?style=popout-square) ![npm](https://img.shields.io/npm/dm/gitfolio.svg?style=popout-square) ![GitHub top language](https://img.shields.io/github/languages/top/imfunniee/gitfolio.svg?style=popout-square) ![GitHub last commit](https://img.shields.io/github/last-commit/imfunniee/gitfolio.svg?style=popout-square) ![GitHub](https://img.shields.io/github/license/imfunniee/gitfolio.svg?style=popout-square) [![code style: prettier](https://img.shields.io/badge/code_style-prettier-ff69b4.svg?style=flat-square)](https://github.com/prettier/prettier)
|
||||
|
||||
### personal website + blog for every github user
|
||||
|
||||
Gitfolio will help you get started with a portfolio website where you could showcase your work + a blog that will help you spread your ideas into real world.
|
||||
|
||||
Check out this [live demo](https://imfunniee.github.io/gitfolio/) to see gitfolio in action.
|
||||
|
||||
# Getting Started
|
||||
|
||||
### Let's Install
|
||||
|
||||
Install gitfolio
|
||||
|
||||
```sh
|
||||
npm i gitfolio -g
|
||||
```
|
||||
|
||||
### Let's Build
|
||||
|
||||
Using the UI
|
||||
|
||||
```sh
|
||||
$ gitfolio ui
|
||||
```
|
||||
|
||||
> Tip: You can use ui to create new blogs and for updating your folio too.
|
||||
|
||||
or
|
||||
|
||||
```sh
|
||||
gitfolio build <username>
|
||||
```
|
||||
|
||||
`<username>` is your username on github. This will build your website using your GitHub username and put it in the `/dist` folder.
|
||||
|
||||
To run your website use `run` command, Default port is 3000
|
||||
|
||||
```sh
|
||||
gitfolio run -p [port]
|
||||
```
|
||||
|
||||
🎉 Congrats, you just made yourself a personal website!
|
||||
|
||||
### Let's Customize
|
||||
|
||||
#### Forks
|
||||
|
||||
To include forks on your personal website just provide `-f` or `--fork` argument while building
|
||||
|
||||
```sh
|
||||
$ gitfolio build <username> -f
|
||||
```
|
||||
|
||||
#### Sorting Repos
|
||||
|
||||
To sort repos provide `--sort [sortBy]` argument while building. Where `[sortBy]` can be `star`, `created`, `updated`, `pushed`,`full_name`. Default: `created`
|
||||
|
||||
```sh
|
||||
$ gitfolio build <username> --sort star
|
||||
```
|
||||
|
||||
#### Ordering Repos
|
||||
|
||||
To order the sorted repos provide `--order [orderBy]` argument while building. Where `[orderBy]` can be `asc` or `desc`. Default: `asc`
|
||||
|
||||
```sh
|
||||
$ gitfolio build <username> --sort star --order desc
|
||||
```
|
||||
|
||||
#### Customize Themes
|
||||
|
||||
Themes are specified using the `--theme [theme-name]` flag when running the `build` command. The available themes are
|
||||
|
||||
- `light`
|
||||
- `dark`
|
||||
|
||||
> TODO: Add more themes
|
||||
|
||||
For example, the following command will build the website with the dark theme
|
||||
|
||||
```sh
|
||||
$ gitfolio build <username> --theme dark
|
||||
```
|
||||
|
||||
#### Customize background image
|
||||
|
||||
To customize the background image just provide `--background [url]` argument while building
|
||||
|
||||
```sh
|
||||
$ gitfolio build <username> --background https://images.unsplash.com/photo-1557277770-baf0ca74f908?w=1634
|
||||
```
|
||||
|
||||
You could also add in your custom CSS inside `index.css` to give it a more personal feel.
|
||||
|
||||
#### Add Social Media links on your profile
|
||||
|
||||
Twitter, LinkedIn, Medium & Dribbble links to your profile while building
|
||||
|
||||
```sh
|
||||
gitfolio build <username> --twitter <twitter_username> --linkedin <linkedin_username> --medium <medium_username> --dribbble <dribbble_username>
|
||||
```
|
||||
|
||||
### Let's Publish
|
||||
|
||||
Head over to GitHub and create a new repository named `username.github.io`, where username is your username. Push the files inside`/dist` folder to repo you just created.
|
||||
|
||||
Go To `username.github.io` your site should be up!!
|
||||
|
||||
### Updating
|
||||
|
||||
To update your info, simply run
|
||||
|
||||
```sh
|
||||
$ gitfolio update
|
||||
```
|
||||
|
||||
or use the `Update` options in gitfolio's UI
|
||||
|
||||
This will update your info and your repository info.
|
||||
|
||||
To Update background or theme you need to run `build` command again.
|
||||
|
||||
### Add a Blog
|
||||
|
||||
To add your first blog use the UI.
|
||||
|
||||
```sh
|
||||
$ gitfolio ui
|
||||
```
|
||||
|
||||
This will open up a UI page and you can click on `New Blog` to create a new blog. Once you are done writing your blog you can hit the `Create Blog`.
|
||||
|
||||
This will create a blog inside `./dist/blog` folder.
|
||||
|
||||
Look for success or error in your terminal.
|
||||
|
||||
This also adds content to `blog.json` file. This file helps in showcasing your blogs on your personal website as [cards](https://imfunniee.github.io/gitfolio/#blog_section). You could customize the JSON object that corresponds your current blog.
|
||||
|
||||
Blog Demo? [here](https://imfunniee.github.io/gitfolio/blog/my-first-post/)
|
||||
|
||||
Blog's default JSON Format
|
||||
|
||||
```
|
||||
{
|
||||
"url_title": "my-first-blog", // the title you provide while creating a new blog, this appears in url
|
||||
"title": "Lorem ipsum dolor sit amet", // main title of blog
|
||||
"sub_title": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.", // sub-title of blog
|
||||
"top_image": "https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1450", // main image of blog
|
||||
"visible": true // don't worry about this
|
||||
}
|
||||
```
|
||||
|
||||
### Follow me on twitter for more updates [@imfunnieee](https://twitter.com/imfunnieee)
|
||||
|
||||
### License
|
||||
|
||||
![GitHub](https://img.shields.io/github/license/imfunniee/gitfolio.svg?style=popout-square)
|
||||
|
|
132
api.js
132
api.js
|
@ -1,66 +1,66 @@
|
|||
const got = require("got");
|
||||
|
||||
/**
|
||||
* The defaults here are the same as the API
|
||||
* @see https://developer.github.com/v3/repos/#list-user-repositories
|
||||
* @param {string} username
|
||||
* @param {Object} opts
|
||||
* @param {('all' | 'owner' | 'member')[]} [opts.types]
|
||||
* @param {'created' | 'updated' | 'pushed' | 'full_name' | 'star'} [opts.sort]
|
||||
* @param {'desc' | 'asc'} [opts.order]
|
||||
*/
|
||||
async function getRepos(username, opts = {}) {
|
||||
let tempRepos;
|
||||
let page = 1;
|
||||
let repos = [];
|
||||
|
||||
const sort = opts.sort;
|
||||
const order = opts.order || (sort === "full_name" ? "asc" : "desc");
|
||||
const types = opts.types || [];
|
||||
let type = "all";
|
||||
|
||||
if (
|
||||
types.includes("all") ||
|
||||
(types.includes("owner") && types.includes("member"))
|
||||
) {
|
||||
type = "all";
|
||||
} else if (types.includes("member")) {
|
||||
type = "member";
|
||||
}
|
||||
|
||||
do {
|
||||
let requestUrl = `https://api.github.com/users/${username}/repos?per_page=100&page=${page++}&type=${type}`;
|
||||
if (sort && sort !== "star") {
|
||||
requestUrl += `&sort=${sort}&direction=${order}`;
|
||||
}
|
||||
tempRepos = await got(requestUrl);
|
||||
tempRepos = JSON.parse(tempRepos.body);
|
||||
repos = repos.concat(tempRepos);
|
||||
} while (tempRepos.length == 100);
|
||||
|
||||
if (sort == "star") {
|
||||
repos = repos.sort(function(a, b) {
|
||||
if (order == "desc") {
|
||||
return b.stargazers_count - a.stargazers_count;
|
||||
} else {
|
||||
return a.stargazers_count - b.stargazers_count;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return repos;
|
||||
}
|
||||
|
||||
/**
|
||||
* @see https://developer.github.com/v3/users/#get-a-single-user
|
||||
* @param {string} username
|
||||
*/
|
||||
async function getUser(username) {
|
||||
const res = await got(`https://api.github.com/users/${username}`);
|
||||
return JSON.parse(res.body);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
getRepos,
|
||||
getUser
|
||||
};
|
||||
const got = require("got");
|
||||
|
||||
/**
|
||||
* The defaults here are the same as the API
|
||||
* @see https://developer.github.com/v3/repos/#list-user-repositories
|
||||
* @param {string} username
|
||||
* @param {Object} opts
|
||||
* @param {('all' | 'owner' | 'member')[]} [opts.types]
|
||||
* @param {'created' | 'updated' | 'pushed' | 'full_name' | 'star'} [opts.sort]
|
||||
* @param {'desc' | 'asc'} [opts.order]
|
||||
*/
|
||||
async function getRepos(username, opts = {}) {
|
||||
let tempRepos;
|
||||
let page = 1;
|
||||
let repos = [];
|
||||
|
||||
const sort = opts.sort;
|
||||
const order = opts.order || (sort === "full_name" ? "asc" : "desc");
|
||||
const types = opts.types || [];
|
||||
let type = "all";
|
||||
|
||||
if (
|
||||
types.includes("all") ||
|
||||
(types.includes("owner") && types.includes("member"))
|
||||
) {
|
||||
type = "all";
|
||||
} else if (types.includes("member")) {
|
||||
type = "member";
|
||||
}
|
||||
|
||||
do {
|
||||
let requestUrl = `https://api.github.com/users/${username}/repos?per_page=100&page=${page++}&type=${type}`;
|
||||
if (sort && sort !== "star") {
|
||||
requestUrl += `&sort=${sort}&direction=${order}`;
|
||||
}
|
||||
tempRepos = await got(requestUrl);
|
||||
tempRepos = JSON.parse(tempRepos.body);
|
||||
repos = repos.concat(tempRepos);
|
||||
} while (tempRepos.length == 100);
|
||||
|
||||
if (sort == "star") {
|
||||
repos = repos.sort(function(a, b) {
|
||||
if (order == "desc") {
|
||||
return b.stargazers_count - a.stargazers_count;
|
||||
} else {
|
||||
return a.stargazers_count - b.stargazers_count;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
return repos;
|
||||
}
|
||||
|
||||
/**
|
||||
* @see https://developer.github.com/v3/users/#get-a-single-user
|
||||
* @param {string} username
|
||||
*/
|
||||
async function getUser(username) {
|
||||
const res = await got(`https://api.github.com/users/${username}`);
|
||||
return JSON.parse(res.body);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
getRepos,
|
||||
getUser
|
||||
};
|
||||
|
|
|
@ -1,125 +1,125 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
|
||||
<title>Lorem ipsum dolor</title>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.7.0/animate.min.css"
|
||||
/>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://use.fontawesome.com/releases/v5.7.1/css/all.css"
|
||||
integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr"
|
||||
crossorigin="anonymous"
|
||||
/>
|
||||
<script
|
||||
src="https://code.jquery.com/jquery-3.4.1.min.js"
|
||||
integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo="
|
||||
crossorigin="anonymous"
|
||||
></script>
|
||||
</head>
|
||||
<body>
|
||||
<div id="loading">
|
||||
<div id="spinner"></div>
|
||||
</div>
|
||||
<a href="/" class="go_back"><i class="fas fa-arrow-left"></i></a>
|
||||
<div id="background_overlay"></div>
|
||||
<div id="background"></div>
|
||||
<table id="profile_blog">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td style="width:8vw;"><div id="profile_img_blog"></div></td>
|
||||
<td style="width:52vw;">
|
||||
<div id="username_blog"></div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<div id="blog-display">
|
||||
<h1 id="blog_title">Lorem ipsum dolor</h1>
|
||||
<h2 id="blog_sub_title">
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
|
||||
</h2>
|
||||
<div id="blog">
|
||||
<img
|
||||
src="https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1450"
|
||||
/>
|
||||
<p>
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Ut placerat
|
||||
pretium sem, ac maximus dui sodales a. Nunc aliquet hendrerit turpis
|
||||
ac egestas. Phasellus volutpat tristique maximus.
|
||||
<b>Pellentesque feugiat eget nisi et dignissim.</b> Nam nibh erat,
|
||||
sollicitudin non facilisis nec, scelerisque nec ipsum. Sed accumsan
|
||||
velit condimentum, pharetra felis vitae, commodo tellus.
|
||||
<u><i>Mauris consequat luctus orci.</i></u>
|
||||
</p>
|
||||
<p>
|
||||
Vivamus pharetra lobortis dui non tincidunt. Mauris vitae nisi
|
||||
vestibulum, mollis magna a, maximus mi. Suspendisse dictum eget augue
|
||||
quis sodales. Quisque rutrum ligula nec dapibus tincidunt.
|
||||
<span
|
||||
>Proin hendrerit massa a tellus vestibulum, a hendrerit ipsum
|
||||
iaculis. Suspendisse potenti.</span
|
||||
>
|
||||
Praesent eget erat blandit, finibus sapien vitae, ullamcorper erat.
|
||||
Integer blandit, felis at ullamcorper maximus, odio lectus pretium
|
||||
mauris, vel consequat lectus quam eu risus. Pellentesque gravida nec
|
||||
diam eget vehicula.
|
||||
</p>
|
||||
<img
|
||||
src="https://images.unsplash.com/photo-1556814278-8906c7d3a05f?w=1050"
|
||||
/>
|
||||
<p>
|
||||
Donec hendrerit turpis non libero eleifend dignissim. Mauris non
|
||||
tempor metus, et tristique massa. Integer consequat justo quam, vitae
|
||||
aliquam arcu vestibulum at. Donec porttitor quam in tempus convallis.
|
||||
Praesent feugiat eget eros vitae accumsan. Duis ultricies odio quis
|
||||
nisl volutpat, consectetur imperdiet sem laoreet. Quisque maximus
|
||||
semper ligula at tincidunt. Pellentesque accumsan varius vehicula.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div id="footer_blog">
|
||||
<a href="https://github.com/imfunniee" target="_blank"
|
||||
>made on earth by a human</a
|
||||
>
|
||||
</div>
|
||||
<script type="text/javascript">
|
||||
setTimeout(function() {
|
||||
document.getElementById("loading").classList.add("animated");
|
||||
document.getElementById("loading").classList.add("fadeOut");
|
||||
setTimeout(function() {
|
||||
document.getElementById("loading").classList.remove("animated");
|
||||
document.getElementById("loading").classList.remove("fadeOut");
|
||||
document.getElementById("loading").style.display = "none";
|
||||
}, 800);
|
||||
}, 1500);
|
||||
$.getJSON("../../config.json", function(user) {
|
||||
var icon = document.createElement("link");
|
||||
icon.setAttribute("rel", "icon");
|
||||
icon.setAttribute("href", user[0].userimg);
|
||||
icon.setAttribute("type", "image/png");
|
||||
document.getElementsByTagName("head")[0].appendChild(icon);
|
||||
document.getElementById(
|
||||
"profile_img_blog"
|
||||
).style.background = `url('${user[0].userimg}') center center`;
|
||||
document.getElementById(
|
||||
"username_blog"
|
||||
).innerHTML = `<span style="display:${
|
||||
user[0].name == null || !user[0].name ? "none" : "block"
|
||||
};">${user[0].name}</span>@${user[0].username}<b id="blog_time"></b>`;
|
||||
|
||||
if ((user[0].theme = "dark.css")) {
|
||||
document.querySelector("#background_overlay").style.background =
|
||||
"linear-gradient(0deg, rgba(10, 10, 10, 1), rgba(10, 10, 10, 0.1))";
|
||||
} else {
|
||||
document.querySelector("#background_overlay").style.background =
|
||||
"linear-gradient(0deg, rgba(255, 255, 255, 1), rgba(255, 255, 255, 0.1))";
|
||||
}
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
|
||||
<title>Lorem ipsum dolor</title>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.7.0/animate.min.css"
|
||||
/>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://use.fontawesome.com/releases/v5.7.1/css/all.css"
|
||||
integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr"
|
||||
crossorigin="anonymous"
|
||||
/>
|
||||
<script
|
||||
src="https://code.jquery.com/jquery-3.4.1.min.js"
|
||||
integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo="
|
||||
crossorigin="anonymous"
|
||||
></script>
|
||||
</head>
|
||||
<body>
|
||||
<div id="loading">
|
||||
<div id="spinner"></div>
|
||||
</div>
|
||||
<a href="/" class="go_back"><i class="fas fa-arrow-left"></i></a>
|
||||
<div id="background_overlay"></div>
|
||||
<div id="background"></div>
|
||||
<table id="profile_blog">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td style="width:8vw;"><div id="profile_img_blog"></div></td>
|
||||
<td style="width:52vw;">
|
||||
<div id="username_blog"></div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<div id="blog-display">
|
||||
<h1 id="blog_title">Lorem ipsum dolor</h1>
|
||||
<h2 id="blog_sub_title">
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit.
|
||||
</h2>
|
||||
<div id="blog">
|
||||
<img
|
||||
src="https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1450"
|
||||
/>
|
||||
<p>
|
||||
Lorem ipsum dolor sit amet, consectetur adipiscing elit. Ut placerat
|
||||
pretium sem, ac maximus dui sodales a. Nunc aliquet hendrerit turpis
|
||||
ac egestas. Phasellus volutpat tristique maximus.
|
||||
<b>Pellentesque feugiat eget nisi et dignissim.</b> Nam nibh erat,
|
||||
sollicitudin non facilisis nec, scelerisque nec ipsum. Sed accumsan
|
||||
velit condimentum, pharetra felis vitae, commodo tellus.
|
||||
<u><i>Mauris consequat luctus orci.</i></u>
|
||||
</p>
|
||||
<p>
|
||||
Vivamus pharetra lobortis dui non tincidunt. Mauris vitae nisi
|
||||
vestibulum, mollis magna a, maximus mi. Suspendisse dictum eget augue
|
||||
quis sodales. Quisque rutrum ligula nec dapibus tincidunt.
|
||||
<span
|
||||
>Proin hendrerit massa a tellus vestibulum, a hendrerit ipsum
|
||||
iaculis. Suspendisse potenti.</span
|
||||
>
|
||||
Praesent eget erat blandit, finibus sapien vitae, ullamcorper erat.
|
||||
Integer blandit, felis at ullamcorper maximus, odio lectus pretium
|
||||
mauris, vel consequat lectus quam eu risus. Pellentesque gravida nec
|
||||
diam eget vehicula.
|
||||
</p>
|
||||
<img
|
||||
src="https://images.unsplash.com/photo-1556814278-8906c7d3a05f?w=1050"
|
||||
/>
|
||||
<p>
|
||||
Donec hendrerit turpis non libero eleifend dignissim. Mauris non
|
||||
tempor metus, et tristique massa. Integer consequat justo quam, vitae
|
||||
aliquam arcu vestibulum at. Donec porttitor quam in tempus convallis.
|
||||
Praesent feugiat eget eros vitae accumsan. Duis ultricies odio quis
|
||||
nisl volutpat, consectetur imperdiet sem laoreet. Quisque maximus
|
||||
semper ligula at tincidunt. Pellentesque accumsan varius vehicula.
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div id="footer_blog">
|
||||
<a href="https://github.com/imfunniee" target="_blank"
|
||||
>made on earth by a human</a
|
||||
>
|
||||
</div>
|
||||
<script type="text/javascript">
|
||||
setTimeout(function() {
|
||||
document.getElementById("loading").classList.add("animated");
|
||||
document.getElementById("loading").classList.add("fadeOut");
|
||||
setTimeout(function() {
|
||||
document.getElementById("loading").classList.remove("animated");
|
||||
document.getElementById("loading").classList.remove("fadeOut");
|
||||
document.getElementById("loading").style.display = "none";
|
||||
}, 800);
|
||||
}, 1500);
|
||||
$.getJSON("../../config.json", function(user) {
|
||||
var icon = document.createElement("link");
|
||||
icon.setAttribute("rel", "icon");
|
||||
icon.setAttribute("href", user[0].userimg);
|
||||
icon.setAttribute("type", "image/png");
|
||||
document.getElementsByTagName("head")[0].appendChild(icon);
|
||||
document.getElementById(
|
||||
"profile_img_blog"
|
||||
).style.background = `url('${user[0].userimg}') center center`;
|
||||
document.getElementById(
|
||||
"username_blog"
|
||||
).innerHTML = `<span style="display:${
|
||||
user[0].name == null || !user[0].name ? "none" : "block"
|
||||
};">${user[0].name}</span>@${user[0].username}<b id="blog_time"></b>`;
|
||||
|
||||
if ((user[0].theme = "dark.css")) {
|
||||
document.querySelector("#background_overlay").style.background =
|
||||
"linear-gradient(0deg, rgba(10, 10, 10, 1), rgba(10, 10, 10, 0.1))";
|
||||
} else {
|
||||
document.querySelector("#background_overlay").style.background =
|
||||
"linear-gradient(0deg, rgba(255, 255, 255, 1), rgba(255, 255, 255, 0.1))";
|
||||
}
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
1094
assets/index.css
1094
assets/index.css
File diff suppressed because it is too large
Load diff
|
@ -1,121 +1,121 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
|
||||
<title></title>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.7.0/animate.min.css"
|
||||
/>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://use.fontawesome.com/releases/v5.7.1/css/all.css"
|
||||
integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr"
|
||||
crossorigin="anonymous"
|
||||
/>
|
||||
<script
|
||||
src="https://code.jquery.com/jquery-3.4.1.min.js"
|
||||
integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo="
|
||||
crossorigin="anonymous"
|
||||
></script>
|
||||
<script src="https://unpkg.com/magic-grid/dist/magic-grid.min.js"></script>
|
||||
<link rel="stylesheet" href="index.css" />
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<div id="loading">
|
||||
<div id="spinner"></div>
|
||||
</div>
|
||||
<div id="profile">
|
||||
<div id="profile_img"></div>
|
||||
<div id="username">
|
||||
<div id="fullname"></div>
|
||||
</div>
|
||||
<div id="userbio"></div>
|
||||
<div id="about"></div>
|
||||
</div>
|
||||
<div id="display">
|
||||
<div id="work">
|
||||
<h1>Work.</h1>
|
||||
<div class="projects" id="work_section"></div>
|
||||
</div>
|
||||
<div id="forks" style="display:none;">
|
||||
<h1>Forks.</h1>
|
||||
<div class="projects" id="forks_section"></div>
|
||||
</div>
|
||||
<div id="blog_section">
|
||||
<h1>Blog.</h1>
|
||||
<div id="blogs"></div>
|
||||
</div>
|
||||
<div id="footer">
|
||||
<a href="https://github.com/imfunniee" target="_blank"
|
||||
>made on earth by a human</a
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
<script type="text/javascript">
|
||||
setTimeout(function() {
|
||||
document.getElementById("loading").classList.add("animated");
|
||||
document.getElementById("loading").classList.add("fadeOut");
|
||||
setTimeout(function() {
|
||||
document.getElementById("loading").classList.remove("animated");
|
||||
document.getElementById("loading").classList.remove("fadeOut");
|
||||
document.getElementById("loading").style.display = "none";
|
||||
}, 800);
|
||||
}, 1500);
|
||||
$.getJSON("blog.json", function(blog) {
|
||||
blog = blog || [];
|
||||
if (blog.length == 0) {
|
||||
return (document.getElementById("blog_section").style.display =
|
||||
"none");
|
||||
}
|
||||
for (var i = 0; i < blog.length; i++) {
|
||||
$("#blogs").append(`
|
||||
<a href="./blog/${blog[i].url_title}/" target="_blank">
|
||||
<section>
|
||||
<img src="./blog/${blog[i].url_title}/${blog[i].top_image}">
|
||||
<div class="blog_container">
|
||||
<div class="section_title">${blog[i].title}</div>
|
||||
<div class="about_section">
|
||||
${blog[i].sub_title}
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</a>
|
||||
`);
|
||||
}
|
||||
}).fail(function() {
|
||||
return (document.getElementById("blog_section").style.display = "none");
|
||||
});
|
||||
</script>
|
||||
|
||||
<script>
|
||||
const magicProjectsGrid = new MagicGrid({
|
||||
container: "#work_section",
|
||||
animate: false,
|
||||
gutter: 30, // default gutter size
|
||||
static: true,
|
||||
useMin: false,
|
||||
maxColumns: 2,
|
||||
useTransform: true
|
||||
});
|
||||
|
||||
const magicForksGrid = new MagicGrid({
|
||||
container: "#forks_section",
|
||||
animate: false,
|
||||
gutter: 30, // default gutter size
|
||||
static: true,
|
||||
useMin: false,
|
||||
maxColumns: 2,
|
||||
useTransform: true
|
||||
});
|
||||
|
||||
$("document").ready(() => {
|
||||
magicProjectsGrid.listen();
|
||||
magicForksGrid.listen();
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
|
||||
<title></title>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.7.0/animate.min.css"
|
||||
/>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://use.fontawesome.com/releases/v5.7.1/css/all.css"
|
||||
integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr"
|
||||
crossorigin="anonymous"
|
||||
/>
|
||||
<script
|
||||
src="https://code.jquery.com/jquery-3.4.1.min.js"
|
||||
integrity="sha256-CSXorXvZcTkaix6Yvo6HppcZGetbYMGWSFlBw8HfCJo="
|
||||
crossorigin="anonymous"
|
||||
></script>
|
||||
<script src="https://unpkg.com/magic-grid/dist/magic-grid.min.js"></script>
|
||||
<link rel="stylesheet" href="index.css" />
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<div id="loading">
|
||||
<div id="spinner"></div>
|
||||
</div>
|
||||
<div id="profile">
|
||||
<div id="profile_img"></div>
|
||||
<div id="username">
|
||||
<div id="fullname"></div>
|
||||
</div>
|
||||
<div id="userbio"></div>
|
||||
<div id="about"></div>
|
||||
</div>
|
||||
<div id="display">
|
||||
<div id="work">
|
||||
<h1>Work.</h1>
|
||||
<div class="projects" id="work_section"></div>
|
||||
</div>
|
||||
<div id="forks" style="display:none;">
|
||||
<h1>Forks.</h1>
|
||||
<div class="projects" id="forks_section"></div>
|
||||
</div>
|
||||
<div id="blog_section">
|
||||
<h1>Blog.</h1>
|
||||
<div id="blogs"></div>
|
||||
</div>
|
||||
<div id="footer">
|
||||
<a href="https://github.com/imfunniee" target="_blank"
|
||||
>made on earth by a human</a
|
||||
>
|
||||
</div>
|
||||
</div>
|
||||
<script type="text/javascript">
|
||||
setTimeout(function() {
|
||||
document.getElementById("loading").classList.add("animated");
|
||||
document.getElementById("loading").classList.add("fadeOut");
|
||||
setTimeout(function() {
|
||||
document.getElementById("loading").classList.remove("animated");
|
||||
document.getElementById("loading").classList.remove("fadeOut");
|
||||
document.getElementById("loading").style.display = "none";
|
||||
}, 800);
|
||||
}, 1500);
|
||||
$.getJSON("blog.json", function(blog) {
|
||||
blog = blog || [];
|
||||
if (blog.length == 0) {
|
||||
return (document.getElementById("blog_section").style.display =
|
||||
"none");
|
||||
}
|
||||
for (var i = 0; i < blog.length; i++) {
|
||||
$("#blogs").append(`
|
||||
<a href="./blog/${blog[i].url_title}/" target="_blank">
|
||||
<section>
|
||||
<img src="./blog/${blog[i].url_title}/${blog[i].top_image}">
|
||||
<div class="blog_container">
|
||||
<div class="section_title">${blog[i].title}</div>
|
||||
<div class="about_section">
|
||||
${blog[i].sub_title}
|
||||
</div>
|
||||
</div>
|
||||
</section>
|
||||
</a>
|
||||
`);
|
||||
}
|
||||
}).fail(function() {
|
||||
return (document.getElementById("blog_section").style.display = "none");
|
||||
});
|
||||
</script>
|
||||
|
||||
<script>
|
||||
const magicProjectsGrid = new MagicGrid({
|
||||
container: "#work_section",
|
||||
animate: false,
|
||||
gutter: 30, // default gutter size
|
||||
static: true,
|
||||
useMin: false,
|
||||
maxColumns: 2,
|
||||
useTransform: true
|
||||
});
|
||||
|
||||
const magicForksGrid = new MagicGrid({
|
||||
container: "#forks_section",
|
||||
animate: false,
|
||||
gutter: 30, // default gutter size
|
||||
static: true,
|
||||
useMin: false,
|
||||
maxColumns: 2,
|
||||
useTransform: true
|
||||
});
|
||||
|
||||
$("document").ready(() => {
|
||||
magicProjectsGrid.listen();
|
||||
magicForksGrid.listen();
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
|
@ -1,49 +1,49 @@
|
|||
:root {
|
||||
--bg-color: rgb(10, 10, 10);
|
||||
--text-color: #fff;
|
||||
--blog-gray-color: rgb(180, 180, 180);
|
||||
--background-image: linear-gradient(
|
||||
90deg,
|
||||
rgba(10, 10, 10, 0.3),
|
||||
rgb(10, 10, 10, 1)
|
||||
),
|
||||
url("{{{background}}}");
|
||||
--background-background: linear-gradient(
|
||||
0deg,
|
||||
rgba(10, 10, 10, 1),
|
||||
rgba(10, 10, 10, 0.6)
|
||||
),
|
||||
url("{{{background}}}") center center fixed;
|
||||
--height: 50vh;
|
||||
}
|
||||
|
||||
#display h1 {
|
||||
-webkit-background-clip: text;
|
||||
background-clip: text;
|
||||
-webkit-text-fill-color: #fff;
|
||||
}
|
||||
|
||||
#blog-display h1 {
|
||||
-webkit-background-clip: text;
|
||||
background-clip: text;
|
||||
-webkit-text-fill-color: #fff;
|
||||
}
|
||||
|
||||
.projects section {
|
||||
background: rgb(20, 20, 20);
|
||||
}
|
||||
|
||||
#blog_section section {
|
||||
background: rgb(20, 20, 20);
|
||||
}
|
||||
|
||||
@media (max-width: 800px) {
|
||||
:root {
|
||||
--background-image: linear-gradient(
|
||||
0deg,
|
||||
rgba(10, 10, 10, 1),
|
||||
rgba(10, 10, 10, 0)
|
||||
),
|
||||
url("{{{background}}}") !important;
|
||||
}
|
||||
}
|
||||
:root {
|
||||
--bg-color: rgb(10, 10, 10);
|
||||
--text-color: #fff;
|
||||
--blog-gray-color: rgb(180, 180, 180);
|
||||
--background-image: linear-gradient(
|
||||
90deg,
|
||||
rgba(10, 10, 10, 0.3),
|
||||
rgb(10, 10, 10, 1)
|
||||
),
|
||||
url("{{{background}}}");
|
||||
--background-background: linear-gradient(
|
||||
0deg,
|
||||
rgba(10, 10, 10, 1),
|
||||
rgba(10, 10, 10, 0.6)
|
||||
),
|
||||
url("{{{background}}}") center center fixed;
|
||||
--height: 50vh;
|
||||
}
|
||||
|
||||
#display h1 {
|
||||
-webkit-background-clip: text;
|
||||
background-clip: text;
|
||||
-webkit-text-fill-color: #fff;
|
||||
}
|
||||
|
||||
#blog-display h1 {
|
||||
-webkit-background-clip: text;
|
||||
background-clip: text;
|
||||
-webkit-text-fill-color: #fff;
|
||||
}
|
||||
|
||||
.projects section {
|
||||
background: rgb(20, 20, 20);
|
||||
}
|
||||
|
||||
#blog_section section {
|
||||
background: rgb(20, 20, 20);
|
||||
}
|
||||
|
||||
@media (max-width: 800px) {
|
||||
:root {
|
||||
--background-image: linear-gradient(
|
||||
0deg,
|
||||
rgba(10, 10, 10, 1),
|
||||
rgba(10, 10, 10, 0)
|
||||
),
|
||||
url("{{{background}}}") !important;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,12 +1,12 @@
|
|||
:root {
|
||||
--bg-color: #fff;
|
||||
--text-color: rgb(10, 10, 10);
|
||||
--blog-gray-color: rgb(80, 80, 80);
|
||||
--background-image: linear-gradient(
|
||||
90deg,
|
||||
rgba(10, 10, 10, 0.4),
|
||||
rgb(10, 10, 10, 0.4)
|
||||
),
|
||||
url("{{{background}}}");
|
||||
--background-background: #fff;
|
||||
}
|
||||
:root {
|
||||
--bg-color: #fff;
|
||||
--text-color: rgb(10, 10, 10);
|
||||
--blog-gray-color: rgb(80, 80, 80);
|
||||
--background-image: linear-gradient(
|
||||
90deg,
|
||||
rgba(10, 10, 10, 0.4),
|
||||
rgb(10, 10, 10, 0.4)
|
||||
),
|
||||
url("{{{background}}}");
|
||||
--background-background: #fff;
|
||||
}
|
||||
|
|
120
bin/gitfolio.js
Normal file → Executable file
120
bin/gitfolio.js
Normal file → Executable file
|
@ -1,60 +1,60 @@
|
|||
#! /usr/bin/env node
|
||||
/* Argument parser */
|
||||
const program = require("commander");
|
||||
|
||||
process.env.OUT_DIR = process.env.OUT_DIR || process.cwd();
|
||||
|
||||
const { buildCommand } = require("../build");
|
||||
const { updateCommand } = require("../update");
|
||||
const { uiCommand } = require("../ui");
|
||||
const { runCommand } = require("../run");
|
||||
const { version } = require("../package.json");
|
||||
|
||||
function collect(val, memo) {
|
||||
memo.push(val);
|
||||
return memo;
|
||||
}
|
||||
|
||||
program
|
||||
.command("build <username>")
|
||||
.description(
|
||||
"Build site with your GitHub username. This will be used to customize your site"
|
||||
)
|
||||
.option("-t, --theme [theme]", "specify a theme to use", "light")
|
||||
.option("-b, --background [background]", "set the background image")
|
||||
.option("-f, --fork", "includes forks with repos")
|
||||
.option("-s, --sort [sort]", "set default sort for repository", "created")
|
||||
.option("-o, --order [order]", "set default order on sort", "asc")
|
||||
.option("-w, --twitter [username]", "specify twitter username")
|
||||
.option("-l, --linkedin [username]", "specify linkedin username")
|
||||
.option("-m, --medium [username]", "specify medium username")
|
||||
.option("-d, --dribbble [username]", "specify dribbble username")
|
||||
.action(buildCommand);
|
||||
|
||||
program
|
||||
.command("update")
|
||||
.description("Update user and repository data")
|
||||
.action(updateCommand);
|
||||
|
||||
program
|
||||
.command("ui")
|
||||
.description("Create and Manage blogs with ease")
|
||||
.action(uiCommand);
|
||||
|
||||
program
|
||||
.command("run")
|
||||
.description("Run build files")
|
||||
.option("-p, --port [port]", "provide a port for localhost, default is 3000")
|
||||
.action(runCommand);
|
||||
|
||||
program.on("command:*", () => {
|
||||
console.log("Unknown Command: " + program.args.join(" "));
|
||||
program.help();
|
||||
});
|
||||
|
||||
program
|
||||
.version(version, "-v --version")
|
||||
.usage("<command> [options]")
|
||||
.parse(process.argv);
|
||||
|
||||
if (program.args.length === 0) program.help();
|
||||
#! /usr/bin/env node
|
||||
/* Argument parser */
|
||||
const program = require("commander");
|
||||
|
||||
process.env.OUT_DIR = process.env.OUT_DIR || process.cwd();
|
||||
|
||||
const { buildCommand } = require("../build");
|
||||
const { updateCommand } = require("../update");
|
||||
const { uiCommand } = require("../ui");
|
||||
const { runCommand } = require("../run");
|
||||
const { version } = require("../package.json");
|
||||
|
||||
function collect(val, memo) {
|
||||
memo.push(val);
|
||||
return memo;
|
||||
}
|
||||
|
||||
program
|
||||
.command("build <username>")
|
||||
.description(
|
||||
"Build site with your GitHub username. This will be used to customize your site"
|
||||
)
|
||||
.option("-t, --theme [theme]", "specify a theme to use", "light")
|
||||
.option("-b, --background [background]", "set the background image")
|
||||
.option("-f, --fork", "includes forks with repos")
|
||||
.option("-s, --sort [sort]", "set default sort for repository", "created")
|
||||
.option("-o, --order [order]", "set default order on sort", "asc")
|
||||
.option("-w, --twitter [username]", "specify twitter username")
|
||||
.option("-l, --linkedin [username]", "specify linkedin username")
|
||||
.option("-m, --medium [username]", "specify medium username")
|
||||
.option("-d, --dribbble [username]", "specify dribbble username")
|
||||
.action(buildCommand);
|
||||
|
||||
program
|
||||
.command("update")
|
||||
.description("Update user and repository data")
|
||||
.action(updateCommand);
|
||||
|
||||
program
|
||||
.command("ui")
|
||||
.description("Create and Manage blogs with ease")
|
||||
.action(uiCommand);
|
||||
|
||||
program
|
||||
.command("run")
|
||||
.description("Run build files")
|
||||
.option("-p, --port [port]", "provide a port for localhost, default is 3000")
|
||||
.action(runCommand);
|
||||
|
||||
program.on("command:*", () => {
|
||||
console.log("Unknown Command: " + program.args.join(" "));
|
||||
program.help();
|
||||
});
|
||||
|
||||
program
|
||||
.version(version, "-v --version")
|
||||
.usage("<command> [options]")
|
||||
.parse(process.argv);
|
||||
|
||||
if (program.args.length === 0) program.help();
|
||||
|
|
188
build.js
188
build.js
|
@ -1,94 +1,94 @@
|
|||
/* Filepath utilities */
|
||||
const path = require("path");
|
||||
/* Promise library */
|
||||
const bluebird = require("bluebird");
|
||||
const hbs = require("handlebars");
|
||||
/* Creates promise-returning async functions
|
||||
from callback-passed async functions */
|
||||
const fs = bluebird.promisifyAll(require("fs"));
|
||||
const { updateHTML } = require("./populate");
|
||||
const { getConfig, outDir } = require("./utils");
|
||||
|
||||
const assetDir = path.resolve(`${__dirname}/assets/`);
|
||||
const config = path.join(outDir, "config.json");
|
||||
|
||||
/**
|
||||
* Creates the stylesheet used by the site from a template stylesheet.
|
||||
*
|
||||
* Theme styles are added to the new stylesheet depending on command line
|
||||
* arguments.
|
||||
*/
|
||||
async function populateCSS({
|
||||
theme = "light",
|
||||
background = "https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1500&q=80"
|
||||
} = {}) {
|
||||
/* Get the theme the user requests. Defaults to 'light' */
|
||||
theme = `${theme}.css`;
|
||||
let template = path.resolve(assetDir, "index.css");
|
||||
let stylesheet = path.join(outDir, "index.css");
|
||||
|
||||
try {
|
||||
await fs.accessAsync(outDir, fs.constants.F_OK);
|
||||
} catch (err) {
|
||||
await fs.mkdirAsync(outDir);
|
||||
}
|
||||
/* Copy over the template CSS stylesheet */
|
||||
await fs.copyFileAsync(template, stylesheet);
|
||||
|
||||
/* Get an array of every available theme */
|
||||
let themes = await fs.readdirAsync(path.join(assetDir, "themes"));
|
||||
|
||||
if (!themes.includes(theme)) {
|
||||
console.error('Error: Requested theme not found. Defaulting to "light".');
|
||||
theme = "light";
|
||||
}
|
||||
/* Read in the theme stylesheet */
|
||||
let themeSource = await fs.readFileSync(path.join(assetDir, "themes", theme));
|
||||
themeSource = themeSource.toString("utf-8");
|
||||
let themeTemplate = hbs.compile(themeSource);
|
||||
let styles = themeTemplate({
|
||||
background: `${background}`
|
||||
});
|
||||
/* Add the user-specified styles to the new stylesheet */
|
||||
await fs.appendFileAsync(stylesheet, styles);
|
||||
|
||||
/* Update the config file with the user's theme choice */
|
||||
const data = await getConfig();
|
||||
data[0].theme = theme;
|
||||
await fs.writeFileAsync(config, JSON.stringify(data, null, " "));
|
||||
}
|
||||
|
||||
async function populateConfig(opts) {
|
||||
const data = await getConfig();
|
||||
Object.assign(data[0], opts);
|
||||
await fs.writeFileAsync(config, JSON.stringify(data, null, " "));
|
||||
}
|
||||
|
||||
async function buildCommand(username, program) {
|
||||
await populateCSS(program);
|
||||
let types;
|
||||
if (!program.include || !program.include.length) {
|
||||
types = ["all"];
|
||||
} else {
|
||||
types = program.include;
|
||||
}
|
||||
const opts = {
|
||||
sort: program.sort,
|
||||
order: program.order,
|
||||
includeFork: program.fork ? true : false,
|
||||
types,
|
||||
twitter: program.twitter,
|
||||
linkedin: program.linkedin,
|
||||
medium: program.medium,
|
||||
dribbble: program.dribbble
|
||||
};
|
||||
|
||||
await populateConfig(opts);
|
||||
updateHTML(("%s", username), opts);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
buildCommand,
|
||||
populateCSS,
|
||||
populateConfig
|
||||
};
|
||||
/* Filepath utilities */
|
||||
const path = require("path");
|
||||
/* Promise library */
|
||||
const bluebird = require("bluebird");
|
||||
const hbs = require("handlebars");
|
||||
/* Creates promise-returning async functions
|
||||
from callback-passed async functions */
|
||||
const fs = bluebird.promisifyAll(require("fs"));
|
||||
const { updateHTML } = require("./populate");
|
||||
const { getConfig, outDir } = require("./utils");
|
||||
|
||||
const assetDir = path.resolve(`${__dirname}/assets/`);
|
||||
const config = path.join(outDir, "config.json");
|
||||
|
||||
/**
|
||||
* Creates the stylesheet used by the site from a template stylesheet.
|
||||
*
|
||||
* Theme styles are added to the new stylesheet depending on command line
|
||||
* arguments.
|
||||
*/
|
||||
async function populateCSS({
|
||||
theme = "light",
|
||||
background = "https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1500&q=80"
|
||||
} = {}) {
|
||||
/* Get the theme the user requests. Defaults to 'light' */
|
||||
theme = `${theme}.css`;
|
||||
let template = path.resolve(assetDir, "index.css");
|
||||
let stylesheet = path.join(outDir, "index.css");
|
||||
|
||||
try {
|
||||
await fs.accessAsync(outDir, fs.constants.F_OK);
|
||||
} catch (err) {
|
||||
await fs.mkdirAsync(outDir);
|
||||
}
|
||||
/* Copy over the template CSS stylesheet */
|
||||
await fs.copyFileAsync(template, stylesheet);
|
||||
|
||||
/* Get an array of every available theme */
|
||||
let themes = await fs.readdirAsync(path.join(assetDir, "themes"));
|
||||
|
||||
if (!themes.includes(theme)) {
|
||||
console.error('Error: Requested theme not found. Defaulting to "light".');
|
||||
theme = "light";
|
||||
}
|
||||
/* Read in the theme stylesheet */
|
||||
let themeSource = await fs.readFileSync(path.join(assetDir, "themes", theme));
|
||||
themeSource = themeSource.toString("utf-8");
|
||||
let themeTemplate = hbs.compile(themeSource);
|
||||
let styles = themeTemplate({
|
||||
background: `${background}`
|
||||
});
|
||||
/* Add the user-specified styles to the new stylesheet */
|
||||
await fs.appendFileAsync(stylesheet, styles);
|
||||
|
||||
/* Update the config file with the user's theme choice */
|
||||
const data = await getConfig();
|
||||
data[0].theme = theme;
|
||||
await fs.writeFileAsync(config, JSON.stringify(data, null, " "));
|
||||
}
|
||||
|
||||
async function populateConfig(opts) {
|
||||
const data = await getConfig();
|
||||
Object.assign(data[0], opts);
|
||||
await fs.writeFileAsync(config, JSON.stringify(data, null, " "));
|
||||
}
|
||||
|
||||
async function buildCommand(username, program) {
|
||||
await populateCSS(program);
|
||||
let types;
|
||||
if (!program.include || !program.include.length) {
|
||||
types = ["all"];
|
||||
} else {
|
||||
types = program.include;
|
||||
}
|
||||
const opts = {
|
||||
sort: program.sort,
|
||||
order: program.order,
|
||||
includeFork: program.fork ? true : false,
|
||||
types,
|
||||
twitter: program.twitter,
|
||||
linkedin: program.linkedin,
|
||||
medium: program.medium,
|
||||
dribbble: program.dribbble
|
||||
};
|
||||
|
||||
await populateConfig(opts);
|
||||
updateHTML(("%s", username), opts);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
buildCommand,
|
||||
populateCSS,
|
||||
populateConfig
|
||||
};
|
||||
|
|
|
@ -1,11 +1,11 @@
|
|||
[
|
||||
{
|
||||
"username": null,
|
||||
"name": null,
|
||||
"userimg": null,
|
||||
"sort": null,
|
||||
"order": null,
|
||||
"includeFork": null,
|
||||
"theme": "light.css"
|
||||
}
|
||||
]
|
||||
[
|
||||
{
|
||||
"username": null,
|
||||
"name": null,
|
||||
"userimg": null,
|
||||
"sort": null,
|
||||
"order": null,
|
||||
"includeFork": null,
|
||||
"theme": "light.css"
|
||||
}
|
||||
]
|
||||
|
|
2596
package-lock.json
generated
2596
package-lock.json
generated
File diff suppressed because it is too large
Load diff
96
package.json
96
package.json
|
@ -1,48 +1,48 @@
|
|||
{
|
||||
"name": "gitfolio",
|
||||
"version": "0.1.5",
|
||||
"description": "a portfolio website for everyone to showcase their work",
|
||||
"main": "build.js",
|
||||
"bin": "bin/gitfolio.js",
|
||||
"scripts": {
|
||||
"cli": "OUT_DIR='./dist' node bin/gitfolio.js",
|
||||
"clean": "rm -rf ./dist/*",
|
||||
"prettier": "prettier --write \"./**/*.{js,jsx,json,html,css,md}\"",
|
||||
"test": "echo \"Error: no test specified\" && exit 1"
|
||||
},
|
||||
"author": {
|
||||
"name": "@imfunniee and community",
|
||||
"email": "imfunny@wybemf.com",
|
||||
"url": "https://imfunniee.github.io"
|
||||
},
|
||||
"bugs": "https://github.com/imfunniee/gitfolio/issues",
|
||||
"homepage": "https://github.com/imfunniee/gitfolio",
|
||||
"keywords": [
|
||||
"personal-website",
|
||||
"github",
|
||||
"portfolio",
|
||||
"portfolio website",
|
||||
"blog website",
|
||||
"blog",
|
||||
"gitfolio",
|
||||
"git"
|
||||
],
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/imfunniee/gitfolio"
|
||||
},
|
||||
"license": "GPL-3.0",
|
||||
"dependencies": {
|
||||
"bluebird": "^3.5.4",
|
||||
"body-parser": "^1.19.0",
|
||||
"commander": "^2.20.0",
|
||||
"ejs": "^2.6.2",
|
||||
"express": "^4.17.0",
|
||||
"github-emoji": "^1.1.1",
|
||||
"got": "^9.6.0",
|
||||
"handlebars": "^4.1.2",
|
||||
"jsdom": "^15.1.0",
|
||||
"ncp": "^2.0.0",
|
||||
"prettier": "^1.18.2"
|
||||
}
|
||||
}
|
||||
{
|
||||
"name": "gitfolio",
|
||||
"version": "0.1.5",
|
||||
"description": "a portfolio website for everyone to showcase their work",
|
||||
"main": "build.js",
|
||||
"bin": "bin/gitfolio.js",
|
||||
"scripts": {
|
||||
"cli": "OUT_DIR='./dist' node bin/gitfolio.js",
|
||||
"clean": "rm -rf ./dist/*",
|
||||
"prettier": "prettier --write \"./**/*.{js,jsx,json,html,css,md}\"",
|
||||
"test": "echo \"Error: no test specified\" && exit 1"
|
||||
},
|
||||
"author": {
|
||||
"name": "@imfunniee and community",
|
||||
"email": "imfunny@wybemf.com",
|
||||
"url": "https://imfunniee.github.io"
|
||||
},
|
||||
"bugs": "https://github.com/imfunniee/gitfolio/issues",
|
||||
"homepage": "https://github.com/imfunniee/gitfolio",
|
||||
"keywords": [
|
||||
"personal-website",
|
||||
"github",
|
||||
"portfolio",
|
||||
"portfolio website",
|
||||
"blog website",
|
||||
"blog",
|
||||
"gitfolio",
|
||||
"git"
|
||||
],
|
||||
"repository": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/imfunniee/gitfolio"
|
||||
},
|
||||
"license": "GPL-3.0",
|
||||
"dependencies": {
|
||||
"bluebird": "^3.5.4",
|
||||
"body-parser": "^1.19.0",
|
||||
"commander": "^2.20.0",
|
||||
"ejs": "^2.6.2",
|
||||
"express": "^4.17.0",
|
||||
"github-emoji": "^1.1.1",
|
||||
"got": "^9.6.0",
|
||||
"handlebars": "^4.1.2",
|
||||
"jsdom": "^15.1.0",
|
||||
"ncp": "^2.0.0",
|
||||
"prettier": "^1.18.2"
|
||||
}
|
||||
}
|
||||
|
|
344
populate.js
344
populate.js
|
@ -1,172 +1,172 @@
|
|||
const fs = require("fs");
|
||||
const emoji = require("github-emoji");
|
||||
const jsdom = require("jsdom").JSDOM,
|
||||
options = {
|
||||
resources: "usable"
|
||||
};
|
||||
const { getConfig, outDir } = require("./utils");
|
||||
const { getRepos, getUser } = require("./api");
|
||||
|
||||
function convertToEmoji(text) {
|
||||
if (text == null) return;
|
||||
text = text.toString();
|
||||
var pattern = /(?<=:\s*).*?(?=\s*:)/gs;
|
||||
if (text.match(pattern) != null) {
|
||||
var str = text.match(pattern);
|
||||
str = str.filter(function(arr) {
|
||||
return /\S/.test(arr);
|
||||
});
|
||||
for (i = 0; i < str.length; i++) {
|
||||
if (emoji.URLS[str[i]] != undefined) {
|
||||
text = text.replace(
|
||||
`:${str[i]}:`,
|
||||
`<img src="${emoji.URLS[str[i]]}" class="emoji">`
|
||||
);
|
||||
}
|
||||
}
|
||||
return text;
|
||||
} else {
|
||||
return text;
|
||||
}
|
||||
}
|
||||
|
||||
module.exports.updateHTML = (username, opts) => {
|
||||
const { includeFork, twitter, linkedin, medium, dribbble } = opts;
|
||||
//add data to assets/index.html
|
||||
jsdom
|
||||
.fromFile(`${__dirname}/assets/index.html`, options)
|
||||
.then(function(dom) {
|
||||
let window = dom.window,
|
||||
document = window.document;
|
||||
(async () => {
|
||||
try {
|
||||
console.log("Building HTML/CSS...");
|
||||
const repos = await getRepos(username, opts);
|
||||
|
||||
for (var i = 0; i < repos.length; i++) {
|
||||
let element;
|
||||
if (repos[i].fork == false) {
|
||||
element = document.getElementById("work_section");
|
||||
} else if (includeFork == true) {
|
||||
document.getElementById("forks").style.display = "block";
|
||||
element = document.getElementById("forks_section");
|
||||
} else {
|
||||
continue;
|
||||
}
|
||||
element.innerHTML += `
|
||||
<a href="${repos[i].html_url}" target="_blank">
|
||||
<section>
|
||||
<div class="section_title">${repos[i].name}</div>
|
||||
<div class="about_section">
|
||||
<span style="display:${
|
||||
repos[i].description == undefined
|
||||
? "none"
|
||||
: "block"
|
||||
};">${convertToEmoji(repos[i].description)}</span>
|
||||
</div>
|
||||
<div class="bottom_section">
|
||||
<span style="display:${
|
||||
repos[i].language == null
|
||||
? "none"
|
||||
: "inline-block"
|
||||
};"><i class="fas fa-code"></i> ${
|
||||
repos[i].language
|
||||
}</span>
|
||||
<span><i class="fas fa-star"></i> ${
|
||||
repos[i].stargazers_count
|
||||
}</span>
|
||||
<span><i class="fas fa-code-branch"></i> ${
|
||||
repos[i].forks_count
|
||||
}</span>
|
||||
</div>
|
||||
</section>
|
||||
</a>`;
|
||||
}
|
||||
const user = await getUser(username);
|
||||
document.title = user.login;
|
||||
var icon = document.createElement("link");
|
||||
icon.setAttribute("rel", "icon");
|
||||
icon.setAttribute("href", user.avatar_url);
|
||||
icon.setAttribute("type", "image/png");
|
||||
|
||||
document.getElementsByTagName("head")[0].appendChild(icon);
|
||||
document.getElementById(
|
||||
"profile_img"
|
||||
).style.background = `url('${user.avatar_url}') center center`;
|
||||
document.getElementById(
|
||||
"username"
|
||||
).innerHTML = `<span style="display:${
|
||||
user.name == null || !user.name ? "none" : "block"
|
||||
};">${user.name}</span><a href="${user.html_url}">@${user.login}</a>`;
|
||||
//document.getElementById("github_link").href = `https://github.com/${user.login}`;
|
||||
document.getElementById("userbio").innerHTML = convertToEmoji(
|
||||
user.bio
|
||||
);
|
||||
document.getElementById("userbio").style.display =
|
||||
user.bio == null || !user.bio ? "none" : "block";
|
||||
document.getElementById("about").innerHTML = `
|
||||
<span style="display:${
|
||||
user.company == null || !user.company ? "none" : "block"
|
||||
};"><i class="fas fa-users"></i> ${user.company}</span>
|
||||
<span style="display:${
|
||||
user.email == null || !user.email ? "none" : "block"
|
||||
};"><i class="fas fa-envelope"></i> ${user.email}</span>
|
||||
<span style="display:${
|
||||
user.blog == null || !user.blog ? "none" : "block"
|
||||
};"><i class="fas fa-link"></i> <a href="${user.blog}">${
|
||||
user.blog
|
||||
}</a></span>
|
||||
<span style="display:${
|
||||
user.location == null || !user.location ? "none" : "block"
|
||||
};"><i class="fas fa-map-marker-alt"></i> ${
|
||||
user.location
|
||||
}</span>
|
||||
<span style="display:${
|
||||
user.hireable == false || !user.hireable ? "none" : "block"
|
||||
};"><i class="fas fa-user-tie"></i> Available for hire</span>
|
||||
<div class="socials">
|
||||
<span style="display:${
|
||||
twitter == null ? "none !important" : "block"
|
||||
};"><a href="https://www.twitter.com/${twitter}" target="_blank" class="socials"><i class="fab fa-twitter"></i></a></span>
|
||||
<span style="display:${
|
||||
dribbble == null ? "none !important" : "block"
|
||||
};"><a href="https://www.dribbble.com/${dribbble}" target="_blank" class="socials"><i class="fab fa-dribbble"></i></a></span>
|
||||
<span style="display:${
|
||||
linkedin == null ? "none !important" : "block"
|
||||
};"><a href="https://www.linkedin.com/in/${linkedin}/" target="_blank" class="socials"><i class="fab fa-linkedin-in"></i></a></span>
|
||||
<span style="display:${
|
||||
medium == null ? "none !important" : "block"
|
||||
};"><a href="https://www.medium.com/@${medium}/" target="_blank" class="socials"><i class="fab fa-medium-m"></i></a></span>
|
||||
</div>
|
||||
`;
|
||||
//add data to config.json
|
||||
const data = await getConfig();
|
||||
data[0].username = user.login;
|
||||
data[0].name = user.name;
|
||||
data[0].userimg = user.avatar_url;
|
||||
|
||||
await fs.writeFile(
|
||||
`${outDir}/config.json`,
|
||||
JSON.stringify(data, null, " "),
|
||||
function(err) {
|
||||
if (err) throw err;
|
||||
console.log("Config file updated.");
|
||||
}
|
||||
);
|
||||
await fs.writeFile(
|
||||
`${outDir}/index.html`,
|
||||
"<!DOCTYPE html>" + window.document.documentElement.outerHTML,
|
||||
function(error) {
|
||||
if (error) throw error;
|
||||
console.log(`Build Complete, Files can be Found @ ${outDir}\n`);
|
||||
}
|
||||
);
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
})();
|
||||
})
|
||||
.catch(function(error) {
|
||||
console.log(error);
|
||||
});
|
||||
};
|
||||
const fs = require("fs");
|
||||
const emoji = require("github-emoji");
|
||||
const jsdom = require("jsdom").JSDOM,
|
||||
options = {
|
||||
resources: "usable"
|
||||
};
|
||||
const { getConfig, outDir } = require("./utils");
|
||||
const { getRepos, getUser } = require("./api");
|
||||
|
||||
function convertToEmoji(text) {
|
||||
if (text == null) return;
|
||||
text = text.toString();
|
||||
var pattern = /(?<=:\s*).*?(?=\s*:)/gs;
|
||||
if (text.match(pattern) != null) {
|
||||
var str = text.match(pattern);
|
||||
str = str.filter(function(arr) {
|
||||
return /\S/.test(arr);
|
||||
});
|
||||
for (i = 0; i < str.length; i++) {
|
||||
if (emoji.URLS[str[i]] != undefined) {
|
||||
text = text.replace(
|
||||
`:${str[i]}:`,
|
||||
`<img src="${emoji.URLS[str[i]]}" class="emoji">`
|
||||
);
|
||||
}
|
||||
}
|
||||
return text;
|
||||
} else {
|
||||
return text;
|
||||
}
|
||||
}
|
||||
|
||||
module.exports.updateHTML = (username, opts) => {
|
||||
const { includeFork, twitter, linkedin, medium, dribbble } = opts;
|
||||
//add data to assets/index.html
|
||||
jsdom
|
||||
.fromFile(`${__dirname}/assets/index.html`, options)
|
||||
.then(function(dom) {
|
||||
let window = dom.window,
|
||||
document = window.document;
|
||||
(async () => {
|
||||
try {
|
||||
console.log("Building HTML/CSS...");
|
||||
const repos = await getRepos(username, opts);
|
||||
|
||||
for (var i = 0; i < repos.length; i++) {
|
||||
let element;
|
||||
if (repos[i].fork == false) {
|
||||
element = document.getElementById("work_section");
|
||||
} else if (includeFork == true) {
|
||||
document.getElementById("forks").style.display = "block";
|
||||
element = document.getElementById("forks_section");
|
||||
} else {
|
||||
continue;
|
||||
}
|
||||
element.innerHTML += `
|
||||
<a href="${repos[i].html_url}" target="_blank">
|
||||
<section>
|
||||
<div class="section_title">${repos[i].name}</div>
|
||||
<div class="about_section">
|
||||
<span style="display:${
|
||||
repos[i].description == undefined
|
||||
? "none"
|
||||
: "block"
|
||||
};">${convertToEmoji(repos[i].description)}</span>
|
||||
</div>
|
||||
<div class="bottom_section">
|
||||
<span style="display:${
|
||||
repos[i].language == null
|
||||
? "none"
|
||||
: "inline-block"
|
||||
};"><i class="fas fa-code"></i> ${
|
||||
repos[i].language
|
||||
}</span>
|
||||
<span><i class="fas fa-star"></i> ${
|
||||
repos[i].stargazers_count
|
||||
}</span>
|
||||
<span><i class="fas fa-code-branch"></i> ${
|
||||
repos[i].forks_count
|
||||
}</span>
|
||||
</div>
|
||||
</section>
|
||||
</a>`;
|
||||
}
|
||||
const user = await getUser(username);
|
||||
document.title = user.login;
|
||||
var icon = document.createElement("link");
|
||||
icon.setAttribute("rel", "icon");
|
||||
icon.setAttribute("href", user.avatar_url);
|
||||
icon.setAttribute("type", "image/png");
|
||||
|
||||
document.getElementsByTagName("head")[0].appendChild(icon);
|
||||
document.getElementById(
|
||||
"profile_img"
|
||||
).style.background = `url('${user.avatar_url}') center center`;
|
||||
document.getElementById(
|
||||
"username"
|
||||
).innerHTML = `<span style="display:${
|
||||
user.name == null || !user.name ? "none" : "block"
|
||||
};">${user.name}</span><a href="${user.html_url}">@${user.login}</a>`;
|
||||
//document.getElementById("github_link").href = `https://github.com/${user.login}`;
|
||||
document.getElementById("userbio").innerHTML = convertToEmoji(
|
||||
user.bio
|
||||
);
|
||||
document.getElementById("userbio").style.display =
|
||||
user.bio == null || !user.bio ? "none" : "block";
|
||||
document.getElementById("about").innerHTML = `
|
||||
<span style="display:${
|
||||
user.company == null || !user.company ? "none" : "block"
|
||||
};"><i class="fas fa-users"></i> ${user.company}</span>
|
||||
<span style="display:${
|
||||
user.email == null || !user.email ? "none" : "block"
|
||||
};"><i class="fas fa-envelope"></i> ${user.email}</span>
|
||||
<span style="display:${
|
||||
user.blog == null || !user.blog ? "none" : "block"
|
||||
};"><i class="fas fa-link"></i> <a href="${user.blog}">${
|
||||
user.blog
|
||||
}</a></span>
|
||||
<span style="display:${
|
||||
user.location == null || !user.location ? "none" : "block"
|
||||
};"><i class="fas fa-map-marker-alt"></i> ${
|
||||
user.location
|
||||
}</span>
|
||||
<span style="display:${
|
||||
user.hireable == false || !user.hireable ? "none" : "block"
|
||||
};"><i class="fas fa-user-tie"></i> Available for hire</span>
|
||||
<div class="socials">
|
||||
<span style="display:${
|
||||
twitter == null ? "none !important" : "block"
|
||||
};"><a href="https://www.twitter.com/${twitter}" target="_blank" class="socials"><i class="fab fa-twitter"></i></a></span>
|
||||
<span style="display:${
|
||||
dribbble == null ? "none !important" : "block"
|
||||
};"><a href="https://www.dribbble.com/${dribbble}" target="_blank" class="socials"><i class="fab fa-dribbble"></i></a></span>
|
||||
<span style="display:${
|
||||
linkedin == null ? "none !important" : "block"
|
||||
};"><a href="https://www.linkedin.com/in/${linkedin}/" target="_blank" class="socials"><i class="fab fa-linkedin-in"></i></a></span>
|
||||
<span style="display:${
|
||||
medium == null ? "none !important" : "block"
|
||||
};"><a href="https://www.medium.com/@${medium}/" target="_blank" class="socials"><i class="fab fa-medium-m"></i></a></span>
|
||||
</div>
|
||||
`;
|
||||
//add data to config.json
|
||||
const data = await getConfig();
|
||||
data[0].username = user.login;
|
||||
data[0].name = user.name;
|
||||
data[0].userimg = user.avatar_url;
|
||||
|
||||
await fs.writeFile(
|
||||
`${outDir}/config.json`,
|
||||
JSON.stringify(data, null, " "),
|
||||
function(err) {
|
||||
if (err) throw err;
|
||||
console.log("Config file updated.");
|
||||
}
|
||||
);
|
||||
await fs.writeFile(
|
||||
`${outDir}/index.html`,
|
||||
"<!DOCTYPE html>" + window.document.documentElement.outerHTML,
|
||||
function(error) {
|
||||
if (error) throw error;
|
||||
console.log(`Build Complete, Files can be Found @ ${outDir}\n`);
|
||||
}
|
||||
);
|
||||
} catch (error) {
|
||||
console.log(error);
|
||||
}
|
||||
})();
|
||||
})
|
||||
.catch(function(error) {
|
||||
console.log(error);
|
||||
});
|
||||
};
|
||||
|
|
44
run.js
44
run.js
|
@ -1,22 +1,22 @@
|
|||
const express = require("express");
|
||||
const path = require("path");
|
||||
const outDir = path.resolve("./dist/" || process.env.OUT_DIR);
|
||||
const app = express();
|
||||
app.use(express.static(`${outDir}`));
|
||||
|
||||
function runCommand(program) {
|
||||
let port = program.port ? program.port : 3000;
|
||||
|
||||
app.get("/", function(req, res) {
|
||||
res.sendFile("/index.html");
|
||||
});
|
||||
|
||||
app.listen(port);
|
||||
console.log(
|
||||
`\nGitfolio running on port ${port}, Navigate to http://localhost:${port} in your browser\n`
|
||||
);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
runCommand
|
||||
};
|
||||
const express = require("express");
|
||||
const path = require("path");
|
||||
const outDir = path.resolve("./dist/" || process.env.OUT_DIR);
|
||||
const app = express();
|
||||
app.use(express.static(`${outDir}`));
|
||||
|
||||
function runCommand(program) {
|
||||
let port = program.port ? program.port : 3000;
|
||||
|
||||
app.get("/", function(req, res) {
|
||||
res.sendFile("/index.html");
|
||||
});
|
||||
|
||||
app.listen(port);
|
||||
console.log(
|
||||
`\nGitfolio running on port ${port}, Navigate to http://localhost:${port} in your browser\n`
|
||||
);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
runCommand
|
||||
};
|
||||
|
|
482
ui.js
482
ui.js
|
@ -1,241 +1,241 @@
|
|||
const fs = require("fs");
|
||||
const express = require("express");
|
||||
const { updateHTML } = require("./populate");
|
||||
const { populateCSS, populateConfig } = require("./build");
|
||||
const { updateCommand } = require("./update");
|
||||
const app = express();
|
||||
app.set("view engine", "ejs");
|
||||
app.use(express.static(__dirname + "/views"));
|
||||
app.set("views", __dirname + "/views");
|
||||
app.use(
|
||||
express.json({
|
||||
limit: "50mb"
|
||||
})
|
||||
);
|
||||
app.use(
|
||||
express.urlencoded({
|
||||
limit: "50mb",
|
||||
extended: true
|
||||
})
|
||||
);
|
||||
|
||||
const port = 3000;
|
||||
|
||||
const jsdom = require("jsdom").JSDOM,
|
||||
options = {
|
||||
resources: "usable"
|
||||
};
|
||||
global.DOMParser = new jsdom().window.DOMParser;
|
||||
const { getBlog, outDir } = require("./utils");
|
||||
|
||||
function createBlog(title, subtitle, folder, topImage, images, content) {
|
||||
// Checks to make sure this directory actually exists
|
||||
// and creates it if it doesn't
|
||||
if (!fs.existsSync(`${outDir}/blog/`)) {
|
||||
fs.mkdirSync(
|
||||
`${outDir}/blog/`,
|
||||
{
|
||||
recursive: true
|
||||
},
|
||||
err => {}
|
||||
);
|
||||
}
|
||||
|
||||
if (!fs.existsSync(`${outDir}/blog/${folder}`)) {
|
||||
fs.mkdirSync(`${outDir}/blog/${folder}`, {
|
||||
recursive: true
|
||||
});
|
||||
}
|
||||
|
||||
fs.copyFile(
|
||||
`${__dirname}/assets/blog/blogTemplate.html`,
|
||||
`${outDir}/blog/${folder}/index.html`,
|
||||
err => {
|
||||
if (err) throw err;
|
||||
jsdom
|
||||
.fromFile(`${outDir}/blog/${folder}/index.html`, options)
|
||||
.then(function(dom) {
|
||||
let window = dom.window,
|
||||
document = window.document;
|
||||
let style = document.createElement("link");
|
||||
style.setAttribute("rel", "stylesheet");
|
||||
style.setAttribute("href", "../../index.css");
|
||||
document.getElementsByTagName("head")[0].appendChild(style);
|
||||
|
||||
document.getElementsByTagName("title")[0].textContent = title;
|
||||
document.getElementById("blog_title").textContent = title;
|
||||
document.getElementById("blog_sub_title").textContent = subtitle;
|
||||
document.getElementById(
|
||||
"background"
|
||||
).style.background = `url('top_image.${
|
||||
topImage.split("/")[1].split(";")[0]
|
||||
}') center center`;
|
||||
|
||||
if (content != null) {
|
||||
var parser = new DOMParser();
|
||||
content = parser.parseFromString(content, "text/html");
|
||||
document.getElementById("blog").innerHTML =
|
||||
content.documentElement.innerHTML;
|
||||
}
|
||||
|
||||
images = JSON.parse(images);
|
||||
images.forEach((item, index) => {
|
||||
var base64Image = item.split(";base64,").pop();
|
||||
fs.writeFile(
|
||||
`${outDir}/blog/${folder}/img_${index}.${
|
||||
item.split("/")[1].split(";")[0]
|
||||
}`,
|
||||
base64Image,
|
||||
{
|
||||
encoding: "base64"
|
||||
},
|
||||
function(err) {
|
||||
if (err) throw err;
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
fs.writeFile(
|
||||
`${outDir}/blog/${folder}/index.html`,
|
||||
"<!DOCTYPE html>" + window.document.documentElement.outerHTML,
|
||||
async function(error) {
|
||||
if (error) throw error;
|
||||
|
||||
var base64ImageTop = topImage.split(";base64,").pop();
|
||||
fs.writeFile(
|
||||
`${outDir}/blog/${folder}/top_image.${
|
||||
topImage.split("/")[1].split(";")[0]
|
||||
}`,
|
||||
base64ImageTop,
|
||||
{
|
||||
encoding: "base64"
|
||||
},
|
||||
function(err) {
|
||||
if (err) throw err;
|
||||
}
|
||||
);
|
||||
|
||||
let blog_data = {
|
||||
url_title: folder,
|
||||
title: title,
|
||||
sub_title: subtitle,
|
||||
top_image: `top_image.${topImage.split("/")[1].split(";")[0]}`,
|
||||
visible: true
|
||||
};
|
||||
const old_blogs = await getBlog();
|
||||
old_blogs.push(blog_data);
|
||||
fs.writeFile(
|
||||
`${outDir}/blog.json`,
|
||||
JSON.stringify(old_blogs, null, " "),
|
||||
function(err) {
|
||||
if (err) throw err;
|
||||
console.log(
|
||||
`Blog created successfully at ${outDir}\\blog\\${folder}\n`
|
||||
);
|
||||
}
|
||||
);
|
||||
}
|
||||
);
|
||||
})
|
||||
.catch(function(error) {
|
||||
console.log(error);
|
||||
});
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
function uiCommand() {
|
||||
app.get("/", function(req, res) {
|
||||
res.render("index.ejs");
|
||||
});
|
||||
|
||||
app.get("/update", function(req, res) {
|
||||
if (!fs.existsSync(`${outDir}/config.json`)) {
|
||||
return res.send(
|
||||
'You need to run build command before using update<br><a href="/">Go Back</a>'
|
||||
);
|
||||
}
|
||||
updateCommand();
|
||||
res.redirect("/");
|
||||
});
|
||||
|
||||
app.post("/build", function(req, res) {
|
||||
let username = req.body.username;
|
||||
if (!username) {
|
||||
return res.send("username can't be empty");
|
||||
}
|
||||
let sort = req.body.sort ? req.body.sort : "created";
|
||||
let order = req.body.order ? req.body.order : "asc";
|
||||
let includeFork = req.body.fork == "true" ? true : false;
|
||||
let types = ["owner"];
|
||||
let twitter = req.body.twitter ? req.body.twitter : null;
|
||||
let linkedin = req.body.linkedin ? req.body.linkedin : null;
|
||||
let medium = req.body.medium ? req.body.medium : null;
|
||||
let dribbble = req.body.dribbble ? req.body.dribbble : null;
|
||||
let background = req.body.background
|
||||
? req.body.background
|
||||
: "https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1500&q=80";
|
||||
let theme = req.body.theme == "on" ? "dark" : "light";
|
||||
const opts = {
|
||||
sort: sort,
|
||||
order: order,
|
||||
includeFork: includeFork,
|
||||
types,
|
||||
twitter: twitter,
|
||||
linkedin: linkedin,
|
||||
medium: medium,
|
||||
dribbble: dribbble
|
||||
};
|
||||
|
||||
updateHTML(username, opts);
|
||||
populateCSS({
|
||||
background: background,
|
||||
theme: theme
|
||||
});
|
||||
populateConfig(opts);
|
||||
res.redirect("/");
|
||||
});
|
||||
|
||||
app.get("/blog", function(req, res) {
|
||||
if (!fs.existsSync(`${outDir}/config.json`)) {
|
||||
return res.send(
|
||||
'You need to run build command before accessing blogs<br><a href="/">Go Back</a>'
|
||||
);
|
||||
}
|
||||
fs.readFile(`${outDir}/config.json`, function(err, data) {
|
||||
res.render("blog.ejs", {
|
||||
profile: JSON.parse(data)
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
app.post("/createBlog", function(req, res) {
|
||||
let title = req.body.title;
|
||||
let subtitle = req.body.subtitle;
|
||||
let content = req.body.content ? req.body.content : null;
|
||||
if (!title) {
|
||||
return res.send("title can't be empty");
|
||||
}
|
||||
if (!subtitle) {
|
||||
return res.send("subtitle can't be empty");
|
||||
}
|
||||
if (!content) {
|
||||
return res.send("something isn't working fine, try again :p");
|
||||
}
|
||||
let folder = title.replace(/[^a-zA-Z ]/g, "").replace(/ /g, "-");
|
||||
let topImage = req.body.top_image;
|
||||
let images = req.body.images;
|
||||
createBlog(title, subtitle, folder, topImage, images, content);
|
||||
res.redirect("/blog");
|
||||
});
|
||||
|
||||
console.log("\nStarting...");
|
||||
app.listen(port);
|
||||
console.log(
|
||||
`The GUI is running on port ${port}, Navigate to http://localhost:${port} in your browser\n`
|
||||
);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
uiCommand
|
||||
};
|
||||
const fs = require("fs");
|
||||
const express = require("express");
|
||||
const { updateHTML } = require("./populate");
|
||||
const { populateCSS, populateConfig } = require("./build");
|
||||
const { updateCommand } = require("./update");
|
||||
const app = express();
|
||||
app.set("view engine", "ejs");
|
||||
app.use(express.static(__dirname + "/views"));
|
||||
app.set("views", __dirname + "/views");
|
||||
app.use(
|
||||
express.json({
|
||||
limit: "50mb"
|
||||
})
|
||||
);
|
||||
app.use(
|
||||
express.urlencoded({
|
||||
limit: "50mb",
|
||||
extended: true
|
||||
})
|
||||
);
|
||||
|
||||
const port = 3000;
|
||||
|
||||
const jsdom = require("jsdom").JSDOM,
|
||||
options = {
|
||||
resources: "usable"
|
||||
};
|
||||
global.DOMParser = new jsdom().window.DOMParser;
|
||||
const { getBlog, outDir } = require("./utils");
|
||||
|
||||
function createBlog(title, subtitle, folder, topImage, images, content) {
|
||||
// Checks to make sure this directory actually exists
|
||||
// and creates it if it doesn't
|
||||
if (!fs.existsSync(`${outDir}/blog/`)) {
|
||||
fs.mkdirSync(
|
||||
`${outDir}/blog/`,
|
||||
{
|
||||
recursive: true
|
||||
},
|
||||
err => {}
|
||||
);
|
||||
}
|
||||
|
||||
if (!fs.existsSync(`${outDir}/blog/${folder}`)) {
|
||||
fs.mkdirSync(`${outDir}/blog/${folder}`, {
|
||||
recursive: true
|
||||
});
|
||||
}
|
||||
|
||||
fs.copyFile(
|
||||
`${__dirname}/assets/blog/blogTemplate.html`,
|
||||
`${outDir}/blog/${folder}/index.html`,
|
||||
err => {
|
||||
if (err) throw err;
|
||||
jsdom
|
||||
.fromFile(`${outDir}/blog/${folder}/index.html`, options)
|
||||
.then(function(dom) {
|
||||
let window = dom.window,
|
||||
document = window.document;
|
||||
let style = document.createElement("link");
|
||||
style.setAttribute("rel", "stylesheet");
|
||||
style.setAttribute("href", "../../index.css");
|
||||
document.getElementsByTagName("head")[0].appendChild(style);
|
||||
|
||||
document.getElementsByTagName("title")[0].textContent = title;
|
||||
document.getElementById("blog_title").textContent = title;
|
||||
document.getElementById("blog_sub_title").textContent = subtitle;
|
||||
document.getElementById(
|
||||
"background"
|
||||
).style.background = `url('top_image.${
|
||||
topImage.split("/")[1].split(";")[0]
|
||||
}') center center`;
|
||||
|
||||
if (content != null) {
|
||||
var parser = new DOMParser();
|
||||
content = parser.parseFromString(content, "text/html");
|
||||
document.getElementById("blog").innerHTML =
|
||||
content.documentElement.innerHTML;
|
||||
}
|
||||
|
||||
images = JSON.parse(images);
|
||||
images.forEach((item, index) => {
|
||||
var base64Image = item.split(";base64,").pop();
|
||||
fs.writeFile(
|
||||
`${outDir}/blog/${folder}/img_${index}.${
|
||||
item.split("/")[1].split(";")[0]
|
||||
}`,
|
||||
base64Image,
|
||||
{
|
||||
encoding: "base64"
|
||||
},
|
||||
function(err) {
|
||||
if (err) throw err;
|
||||
}
|
||||
);
|
||||
});
|
||||
|
||||
fs.writeFile(
|
||||
`${outDir}/blog/${folder}/index.html`,
|
||||
"<!DOCTYPE html>" + window.document.documentElement.outerHTML,
|
||||
async function(error) {
|
||||
if (error) throw error;
|
||||
|
||||
var base64ImageTop = topImage.split(";base64,").pop();
|
||||
fs.writeFile(
|
||||
`${outDir}/blog/${folder}/top_image.${
|
||||
topImage.split("/")[1].split(";")[0]
|
||||
}`,
|
||||
base64ImageTop,
|
||||
{
|
||||
encoding: "base64"
|
||||
},
|
||||
function(err) {
|
||||
if (err) throw err;
|
||||
}
|
||||
);
|
||||
|
||||
let blog_data = {
|
||||
url_title: folder,
|
||||
title: title,
|
||||
sub_title: subtitle,
|
||||
top_image: `top_image.${topImage.split("/")[1].split(";")[0]}`,
|
||||
visible: true
|
||||
};
|
||||
const old_blogs = await getBlog();
|
||||
old_blogs.push(blog_data);
|
||||
fs.writeFile(
|
||||
`${outDir}/blog.json`,
|
||||
JSON.stringify(old_blogs, null, " "),
|
||||
function(err) {
|
||||
if (err) throw err;
|
||||
console.log(
|
||||
`Blog created successfully at ${outDir}\\blog\\${folder}\n`
|
||||
);
|
||||
}
|
||||
);
|
||||
}
|
||||
);
|
||||
})
|
||||
.catch(function(error) {
|
||||
console.log(error);
|
||||
});
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
function uiCommand() {
|
||||
app.get("/", function(req, res) {
|
||||
res.render("index.ejs");
|
||||
});
|
||||
|
||||
app.get("/update", function(req, res) {
|
||||
if (!fs.existsSync(`${outDir}/config.json`)) {
|
||||
return res.send(
|
||||
'You need to run build command before using update<br><a href="/">Go Back</a>'
|
||||
);
|
||||
}
|
||||
updateCommand();
|
||||
res.redirect("/");
|
||||
});
|
||||
|
||||
app.post("/build", function(req, res) {
|
||||
let username = req.body.username;
|
||||
if (!username) {
|
||||
return res.send("username can't be empty");
|
||||
}
|
||||
let sort = req.body.sort ? req.body.sort : "created";
|
||||
let order = req.body.order ? req.body.order : "asc";
|
||||
let includeFork = req.body.fork == "true" ? true : false;
|
||||
let types = ["owner"];
|
||||
let twitter = req.body.twitter ? req.body.twitter : null;
|
||||
let linkedin = req.body.linkedin ? req.body.linkedin : null;
|
||||
let medium = req.body.medium ? req.body.medium : null;
|
||||
let dribbble = req.body.dribbble ? req.body.dribbble : null;
|
||||
let background = req.body.background
|
||||
? req.body.background
|
||||
: "https://images.unsplash.com/photo-1553748024-d1b27fb3f960?w=1500&q=80";
|
||||
let theme = req.body.theme == "on" ? "dark" : "light";
|
||||
const opts = {
|
||||
sort: sort,
|
||||
order: order,
|
||||
includeFork: includeFork,
|
||||
types,
|
||||
twitter: twitter,
|
||||
linkedin: linkedin,
|
||||
medium: medium,
|
||||
dribbble: dribbble
|
||||
};
|
||||
|
||||
updateHTML(username, opts);
|
||||
populateCSS({
|
||||
background: background,
|
||||
theme: theme
|
||||
});
|
||||
populateConfig(opts);
|
||||
res.redirect("/");
|
||||
});
|
||||
|
||||
app.get("/blog", function(req, res) {
|
||||
if (!fs.existsSync(`${outDir}/config.json`)) {
|
||||
return res.send(
|
||||
'You need to run build command before accessing blogs<br><a href="/">Go Back</a>'
|
||||
);
|
||||
}
|
||||
fs.readFile(`${outDir}/config.json`, function(err, data) {
|
||||
res.render("blog.ejs", {
|
||||
profile: JSON.parse(data)
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
app.post("/createBlog", function(req, res) {
|
||||
let title = req.body.title;
|
||||
let subtitle = req.body.subtitle;
|
||||
let content = req.body.content ? req.body.content : null;
|
||||
if (!title) {
|
||||
return res.send("title can't be empty");
|
||||
}
|
||||
if (!subtitle) {
|
||||
return res.send("subtitle can't be empty");
|
||||
}
|
||||
if (!content) {
|
||||
return res.send("something isn't working fine, try again :p");
|
||||
}
|
||||
let folder = title.replace(/[^a-zA-Z ]/g, "").replace(/ /g, "-");
|
||||
let topImage = req.body.top_image;
|
||||
let images = req.body.images;
|
||||
createBlog(title, subtitle, folder, topImage, images, content);
|
||||
res.redirect("/blog");
|
||||
});
|
||||
|
||||
console.log("\nStarting...");
|
||||
app.listen(port);
|
||||
console.log(
|
||||
`The GUI is running on port ${port}, Navigate to http://localhost:${port} in your browser\n`
|
||||
);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
uiCommand
|
||||
};
|
||||
|
|
56
update.js
56
update.js
|
@ -1,28 +1,28 @@
|
|||
const { getConfig } = require("./utils");
|
||||
const { updateHTML } = require("./populate");
|
||||
|
||||
async function updateCommand() {
|
||||
const data = await getConfig();
|
||||
var username = data[0].username;
|
||||
if (username == null) {
|
||||
console.log(
|
||||
"username not found in config.json, please run build command before using update"
|
||||
);
|
||||
return;
|
||||
}
|
||||
const opts = {
|
||||
sort: data[0].sort,
|
||||
order: data[0].order,
|
||||
includeFork: data[0].includeFork,
|
||||
types: data[0].types,
|
||||
twitter: data[0].twitter,
|
||||
linkedin: data[0].linkedin,
|
||||
medium: data[0].medium,
|
||||
dribbble: data[0].dribbble
|
||||
};
|
||||
updateHTML(username, opts);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
updateCommand
|
||||
};
|
||||
const { getConfig } = require("./utils");
|
||||
const { updateHTML } = require("./populate");
|
||||
|
||||
async function updateCommand() {
|
||||
const data = await getConfig();
|
||||
var username = data[0].username;
|
||||
if (username == null) {
|
||||
console.log(
|
||||
"username not found in config.json, please run build command before using update"
|
||||
);
|
||||
return;
|
||||
}
|
||||
const opts = {
|
||||
sort: data[0].sort,
|
||||
order: data[0].order,
|
||||
includeFork: data[0].includeFork,
|
||||
types: data[0].types,
|
||||
twitter: data[0].twitter,
|
||||
linkedin: data[0].linkedin,
|
||||
medium: data[0].medium,
|
||||
dribbble: data[0].dribbble
|
||||
};
|
||||
updateHTML(username, opts);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
updateCommand
|
||||
};
|
||||
|
|
78
utils.js
78
utils.js
|
@ -1,39 +1,39 @@
|
|||
const path = require("path");
|
||||
const bluebird = require("bluebird");
|
||||
const fs = bluebird.promisifyAll(require("fs"));
|
||||
|
||||
const outDir = path.resolve("./dist/" || process.env.OUT_DIR);
|
||||
const configPath = path.join(outDir, "config.json");
|
||||
const blogPath = path.join(outDir, "blog.json");
|
||||
|
||||
const defaultConfigPath = path.resolve(`${__dirname}/default/config.json`);
|
||||
const defaultBlogPath = path.resolve(`${__dirname}/default/blog.json`);
|
||||
|
||||
/**
|
||||
* Tries to read file from out dir,
|
||||
* if not present returns default file contents
|
||||
*/
|
||||
async function getFileWithDefaults(file, defaultFile) {
|
||||
try {
|
||||
await fs.accessAsync(file, fs.constants.F_OK);
|
||||
} catch (err) {
|
||||
const defaultData = await fs.readFileAsync(defaultFile);
|
||||
return JSON.parse(defaultData);
|
||||
}
|
||||
const data = await fs.readFileAsync(file);
|
||||
return JSON.parse(data);
|
||||
}
|
||||
|
||||
async function getConfig() {
|
||||
return getFileWithDefaults(configPath, defaultConfigPath);
|
||||
}
|
||||
|
||||
async function getBlog() {
|
||||
return getFileWithDefaults(blogPath, defaultBlogPath);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
outDir,
|
||||
getConfig,
|
||||
getBlog
|
||||
};
|
||||
const path = require("path");
|
||||
const bluebird = require("bluebird");
|
||||
const fs = bluebird.promisifyAll(require("fs"));
|
||||
|
||||
const outDir = path.resolve("./dist/" || process.env.OUT_DIR);
|
||||
const configPath = path.join(outDir, "config.json");
|
||||
const blogPath = path.join(outDir, "blog.json");
|
||||
|
||||
const defaultConfigPath = path.resolve(`${__dirname}/default/config.json`);
|
||||
const defaultBlogPath = path.resolve(`${__dirname}/default/blog.json`);
|
||||
|
||||
/**
|
||||
* Tries to read file from out dir,
|
||||
* if not present returns default file contents
|
||||
*/
|
||||
async function getFileWithDefaults(file, defaultFile) {
|
||||
try {
|
||||
await fs.accessAsync(file, fs.constants.F_OK);
|
||||
} catch (err) {
|
||||
const defaultData = await fs.readFileAsync(defaultFile);
|
||||
return JSON.parse(defaultData);
|
||||
}
|
||||
const data = await fs.readFileAsync(file);
|
||||
return JSON.parse(data);
|
||||
}
|
||||
|
||||
async function getConfig() {
|
||||
return getFileWithDefaults(configPath, defaultConfigPath);
|
||||
}
|
||||
|
||||
async function getBlog() {
|
||||
return getFileWithDefaults(blogPath, defaultBlogPath);
|
||||
}
|
||||
|
||||
module.exports = {
|
||||
outDir,
|
||||
getConfig,
|
||||
getBlog
|
||||
};
|
||||
|
|
518
views/blog.ejs
518
views/blog.ejs
|
@ -1,259 +1,259 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
|
||||
<title>Gitfolio UI</title>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.7.0/animate.min.css"
|
||||
/>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://use.fontawesome.com/releases/v5.7.1/css/all.css"
|
||||
integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr"
|
||||
crossorigin="anonymous"
|
||||
/>
|
||||
<link rel="stylesheet" type="text/css" href="./css/index.css" />
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdn.jsdelivr.net/gh/zeva-ui/zeva/dist/css/zeva.min.css"
|
||||
/>
|
||||
</head>
|
||||
<body class="body-light">
|
||||
<header>
|
||||
<b>gitfolio</b>
|
||||
<a href="/blog" style="float: right">New Blog </a>
|
||||
<a href="/update" style="float: right">Update</a>
|
||||
<a href="/" style="float: right">Home</a>
|
||||
</header>
|
||||
<div id="top_image">
|
||||
<i class="fas fa-camera" onclick="applyTopImage()"></i>
|
||||
</div>
|
||||
<input
|
||||
type="file"
|
||||
id="top_image_file"
|
||||
style="display: none"
|
||||
accept="image/*"
|
||||
style="display: none"
|
||||
/>
|
||||
<table id="profile_blog">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td style="width:8vw;">
|
||||
<div
|
||||
id="profile_img_blog"
|
||||
style="background:url('<%= profile[0].userimg%>') center center;"
|
||||
></div>
|
||||
</td>
|
||||
<td style="width:52vw;">
|
||||
<div id="username_blog">
|
||||
<% if(profile[0].name)%>
|
||||
<span><%= profile[0].name%></span>
|
||||
<% %>
|
||||
<br />@<%= profile[0].username%><b id="blog_time"></b>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<div id="blog-display">
|
||||
<form
|
||||
style="padding: 0px; width:100%;"
|
||||
method="POST"
|
||||
action="/createBlog"
|
||||
id="form"
|
||||
>
|
||||
<textarea
|
||||
id="blog_title"
|
||||
placeholder="blog title here"
|
||||
spellcheck="false"
|
||||
rows="1"
|
||||
onkeyup="addRow(event)"
|
||||
name="title"
|
||||
required
|
||||
></textarea>
|
||||
<br />
|
||||
<textarea
|
||||
id="blog_sub_title"
|
||||
placeholder="blog sub title here"
|
||||
spellcheck="false"
|
||||
rows="1"
|
||||
name="subtitle"
|
||||
onkeyup="addRow(event)"
|
||||
required
|
||||
></textarea>
|
||||
<div id="originalContent" style="display: none"></div>
|
||||
<input type="hidden" name="top_image" id="top" />
|
||||
<input type="hidden" name="content" id="content" />
|
||||
<input type="hidden" name="images" id="images" />
|
||||
<div id="blog"></div>
|
||||
<div class="div_for_buttons">
|
||||
<input
|
||||
type="file"
|
||||
name="file"
|
||||
id="file"
|
||||
style="display: none"
|
||||
accept="image/*"
|
||||
/>
|
||||
<button
|
||||
class="button h-weight-bold h-border-pill -size-small"
|
||||
type="button"
|
||||
onclick="clickFile()"
|
||||
>
|
||||
<i class="fas fa-plus"></i> Image
|
||||
</button>
|
||||
<button
|
||||
class="button h-weight-bold h-border-pill -size-small"
|
||||
type="button"
|
||||
onclick="addPara()"
|
||||
>
|
||||
<i class="fas fa-plus"></i> Paragraph
|
||||
</button>
|
||||
<h5>Tip : You can use html inside paragraphs</h5>
|
||||
</div>
|
||||
<button type="button" class="button" onclick="submitthisform()">
|
||||
Create Blog
|
||||
</button>
|
||||
</form>
|
||||
</div>
|
||||
<script
|
||||
type="text/javascript"
|
||||
src="https://cdn.jsdelivr.net/gh/zeva-ui/zeva/dist/js/index.min.js"
|
||||
></script>
|
||||
<script type="text/javascript">
|
||||
var imgElement = document.querySelector("#file");
|
||||
var topImageElement = document.querySelector("#top_image_file");
|
||||
var img_number = 0;
|
||||
var blog_para_number = 0;
|
||||
var images = [];
|
||||
|
||||
function applyTopImage() {
|
||||
topImageElement.value = "";
|
||||
document.querySelector("#top").value = "";
|
||||
document.querySelector("#top_image").style.background =
|
||||
"linear-gradient(0deg, rgb(250, 250, 250), rgb(220, 220, 220))";
|
||||
topImageElement.click();
|
||||
}
|
||||
|
||||
topImageElement.addEventListener("change", e => {
|
||||
var reader = new FileReader();
|
||||
reader.readAsDataURL(e.target.files[0]);
|
||||
reader.onload = data => {
|
||||
var image = data.target.result;
|
||||
document.querySelector(
|
||||
"#top_image"
|
||||
).style.background = `linear-gradient(0deg, rgba(250, 250, 250, 1), rgba(220, 220, 220, 0)), url('${image}') center center`;
|
||||
document.querySelector("#top").value = image;
|
||||
};
|
||||
});
|
||||
|
||||
function addRow(e) {
|
||||
e.preventDefault();
|
||||
if (e.target.clientHeight < e.target.scrollHeight) {
|
||||
e.target.rows += 1;
|
||||
} else {
|
||||
if (e.target.value == "") {
|
||||
e.target.rows = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function remove(e, element, blobData) {
|
||||
var elem = document.getElementById(element);
|
||||
var elem2 = document.getElementById(`${element}_original`);
|
||||
elem.parentNode.removeChild(e.target);
|
||||
elem.parentNode.removeChild(elem);
|
||||
elem2.parentNode.removeChild(elem2);
|
||||
imgElement.value = "";
|
||||
if (element.split("_")[0] == "img") {
|
||||
images.splice(images.indexOf(blobData), 1);
|
||||
img_number--;
|
||||
}
|
||||
}
|
||||
|
||||
function addDataToOriginalPara(id) {
|
||||
document.querySelector(
|
||||
`#para_${id}_original`
|
||||
).innerHTML = document.querySelector(`#para_${id}`).value;
|
||||
}
|
||||
|
||||
function clickFile() {
|
||||
imgElement.click();
|
||||
}
|
||||
|
||||
imgElement.addEventListener("change", e => {
|
||||
var img = document.createElement("img");
|
||||
var imageblob = URL.createObjectURL(e.target.files[0]);
|
||||
img.setAttribute(
|
||||
"src",
|
||||
`img_${img_number}.${e.target.files[0].type.split("/")[1]}`
|
||||
);
|
||||
img.setAttribute("alt", `blog image ${img_number}`);
|
||||
img.setAttribute("id", `img_${img_number}_original`);
|
||||
|
||||
var img2 = document.createElement("img");
|
||||
img2.setAttribute("src", imageblob);
|
||||
img2.setAttribute("alt", `blog image ${img_number}`);
|
||||
img2.setAttribute("id", `img_${img_number}`);
|
||||
|
||||
var remove = document.createElement("div");
|
||||
remove.setAttribute("class", "remove");
|
||||
remove.setAttribute(
|
||||
"onclick",
|
||||
`remove(event,'img_${img_number}', '${imageblob}')`
|
||||
);
|
||||
remove.innerHTML = '<i class="fas fa-times"></i> Remove';
|
||||
|
||||
document.querySelector("#originalContent").appendChild(img);
|
||||
document.querySelector("#blog").appendChild(img2);
|
||||
document.querySelector("#blog").appendChild(remove);
|
||||
|
||||
var reader = new FileReader();
|
||||
reader.readAsDataURL(e.target.files[0]);
|
||||
reader.onload = data => {
|
||||
images.push(data.target.result);
|
||||
};
|
||||
|
||||
imgElement.value = "";
|
||||
img_number++;
|
||||
});
|
||||
|
||||
function addPara() {
|
||||
var para = document.createElement("textarea");
|
||||
para.setAttribute("class", "para");
|
||||
para.setAttribute("id", `para_${blog_para_number}`);
|
||||
para.setAttribute("spellcheck", false);
|
||||
para.setAttribute("rows", 1);
|
||||
para.setAttribute(
|
||||
"onkeyup",
|
||||
`addRow(event), addDataToOriginalPara('${blog_para_number}')`
|
||||
);
|
||||
para.setAttribute("required", true);
|
||||
para.setAttribute("placeholder", "What's on your Mind?");
|
||||
var remove = document.createElement("div");
|
||||
remove.setAttribute("class", "remove");
|
||||
remove.setAttribute(
|
||||
"onclick",
|
||||
`remove(event,'para_${blog_para_number}', null)`
|
||||
);
|
||||
remove.innerHTML = '<i class="fas fa-times"></i> Remove';
|
||||
var originalPara = document.createElement("p");
|
||||
originalPara.setAttribute("id", `para_${blog_para_number}_original`);
|
||||
document.querySelector("#blog").appendChild(para);
|
||||
document.querySelector("#blog").appendChild(remove);
|
||||
document.querySelector("#originalContent").appendChild(originalPara);
|
||||
blog_para_number++;
|
||||
}
|
||||
|
||||
function submitthisform() {
|
||||
document.querySelector("#content").value = document.querySelector(
|
||||
"#originalContent"
|
||||
).innerHTML;
|
||||
document.querySelector("#images").value = JSON.stringify(images);
|
||||
document.querySelector("#form").submit();
|
||||
}
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
|
||||
<title>Gitfolio UI</title>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.7.0/animate.min.css"
|
||||
/>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://use.fontawesome.com/releases/v5.7.1/css/all.css"
|
||||
integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr"
|
||||
crossorigin="anonymous"
|
||||
/>
|
||||
<link rel="stylesheet" type="text/css" href="./css/index.css" />
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdn.jsdelivr.net/gh/zeva-ui/zeva/dist/css/zeva.min.css"
|
||||
/>
|
||||
</head>
|
||||
<body class="body-light">
|
||||
<header>
|
||||
<b>gitfolio</b>
|
||||
<a href="/blog" style="float: right">New Blog </a>
|
||||
<a href="/update" style="float: right">Update</a>
|
||||
<a href="/" style="float: right">Home</a>
|
||||
</header>
|
||||
<div id="top_image">
|
||||
<i class="fas fa-camera" onclick="applyTopImage()"></i>
|
||||
</div>
|
||||
<input
|
||||
type="file"
|
||||
id="top_image_file"
|
||||
style="display: none"
|
||||
accept="image/*"
|
||||
style="display: none"
|
||||
/>
|
||||
<table id="profile_blog">
|
||||
<tbody>
|
||||
<tr>
|
||||
<td style="width:8vw;">
|
||||
<div
|
||||
id="profile_img_blog"
|
||||
style="background:url('<%= profile[0].userimg%>') center center;"
|
||||
></div>
|
||||
</td>
|
||||
<td style="width:52vw;">
|
||||
<div id="username_blog">
|
||||
<% if(profile[0].name)%>
|
||||
<span><%= profile[0].name%></span>
|
||||
<% %>
|
||||
<br />@<%= profile[0].username%><b id="blog_time"></b>
|
||||
</div>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<div id="blog-display">
|
||||
<form
|
||||
style="padding: 0px; width:100%;"
|
||||
method="POST"
|
||||
action="/createBlog"
|
||||
id="form"
|
||||
>
|
||||
<textarea
|
||||
id="blog_title"
|
||||
placeholder="blog title here"
|
||||
spellcheck="false"
|
||||
rows="1"
|
||||
onkeyup="addRow(event)"
|
||||
name="title"
|
||||
required
|
||||
></textarea>
|
||||
<br />
|
||||
<textarea
|
||||
id="blog_sub_title"
|
||||
placeholder="blog sub title here"
|
||||
spellcheck="false"
|
||||
rows="1"
|
||||
name="subtitle"
|
||||
onkeyup="addRow(event)"
|
||||
required
|
||||
></textarea>
|
||||
<div id="originalContent" style="display: none"></div>
|
||||
<input type="hidden" name="top_image" id="top" />
|
||||
<input type="hidden" name="content" id="content" />
|
||||
<input type="hidden" name="images" id="images" />
|
||||
<div id="blog"></div>
|
||||
<div class="div_for_buttons">
|
||||
<input
|
||||
type="file"
|
||||
name="file"
|
||||
id="file"
|
||||
style="display: none"
|
||||
accept="image/*"
|
||||
/>
|
||||
<button
|
||||
class="button h-weight-bold h-border-pill -size-small"
|
||||
type="button"
|
||||
onclick="clickFile()"
|
||||
>
|
||||
<i class="fas fa-plus"></i> Image
|
||||
</button>
|
||||
<button
|
||||
class="button h-weight-bold h-border-pill -size-small"
|
||||
type="button"
|
||||
onclick="addPara()"
|
||||
>
|
||||
<i class="fas fa-plus"></i> Paragraph
|
||||
</button>
|
||||
<h5>Tip : You can use html inside paragraphs</h5>
|
||||
</div>
|
||||
<button type="button" class="button" onclick="submitthisform()">
|
||||
Create Blog
|
||||
</button>
|
||||
</form>
|
||||
</div>
|
||||
<script
|
||||
type="text/javascript"
|
||||
src="https://cdn.jsdelivr.net/gh/zeva-ui/zeva/dist/js/index.min.js"
|
||||
></script>
|
||||
<script type="text/javascript">
|
||||
var imgElement = document.querySelector("#file");
|
||||
var topImageElement = document.querySelector("#top_image_file");
|
||||
var img_number = 0;
|
||||
var blog_para_number = 0;
|
||||
var images = [];
|
||||
|
||||
function applyTopImage() {
|
||||
topImageElement.value = "";
|
||||
document.querySelector("#top").value = "";
|
||||
document.querySelector("#top_image").style.background =
|
||||
"linear-gradient(0deg, rgb(250, 250, 250), rgb(220, 220, 220))";
|
||||
topImageElement.click();
|
||||
}
|
||||
|
||||
topImageElement.addEventListener("change", e => {
|
||||
var reader = new FileReader();
|
||||
reader.readAsDataURL(e.target.files[0]);
|
||||
reader.onload = data => {
|
||||
var image = data.target.result;
|
||||
document.querySelector(
|
||||
"#top_image"
|
||||
).style.background = `linear-gradient(0deg, rgba(250, 250, 250, 1), rgba(220, 220, 220, 0)), url('${image}') center center`;
|
||||
document.querySelector("#top").value = image;
|
||||
};
|
||||
});
|
||||
|
||||
function addRow(e) {
|
||||
e.preventDefault();
|
||||
if (e.target.clientHeight < e.target.scrollHeight) {
|
||||
e.target.rows += 1;
|
||||
} else {
|
||||
if (e.target.value == "") {
|
||||
e.target.rows = 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
function remove(e, element, blobData) {
|
||||
var elem = document.getElementById(element);
|
||||
var elem2 = document.getElementById(`${element}_original`);
|
||||
elem.parentNode.removeChild(e.target);
|
||||
elem.parentNode.removeChild(elem);
|
||||
elem2.parentNode.removeChild(elem2);
|
||||
imgElement.value = "";
|
||||
if (element.split("_")[0] == "img") {
|
||||
images.splice(images.indexOf(blobData), 1);
|
||||
img_number--;
|
||||
}
|
||||
}
|
||||
|
||||
function addDataToOriginalPara(id) {
|
||||
document.querySelector(
|
||||
`#para_${id}_original`
|
||||
).innerHTML = document.querySelector(`#para_${id}`).value;
|
||||
}
|
||||
|
||||
function clickFile() {
|
||||
imgElement.click();
|
||||
}
|
||||
|
||||
imgElement.addEventListener("change", e => {
|
||||
var img = document.createElement("img");
|
||||
var imageblob = URL.createObjectURL(e.target.files[0]);
|
||||
img.setAttribute(
|
||||
"src",
|
||||
`img_${img_number}.${e.target.files[0].type.split("/")[1]}`
|
||||
);
|
||||
img.setAttribute("alt", `blog image ${img_number}`);
|
||||
img.setAttribute("id", `img_${img_number}_original`);
|
||||
|
||||
var img2 = document.createElement("img");
|
||||
img2.setAttribute("src", imageblob);
|
||||
img2.setAttribute("alt", `blog image ${img_number}`);
|
||||
img2.setAttribute("id", `img_${img_number}`);
|
||||
|
||||
var remove = document.createElement("div");
|
||||
remove.setAttribute("class", "remove");
|
||||
remove.setAttribute(
|
||||
"onclick",
|
||||
`remove(event,'img_${img_number}', '${imageblob}')`
|
||||
);
|
||||
remove.innerHTML = '<i class="fas fa-times"></i> Remove';
|
||||
|
||||
document.querySelector("#originalContent").appendChild(img);
|
||||
document.querySelector("#blog").appendChild(img2);
|
||||
document.querySelector("#blog").appendChild(remove);
|
||||
|
||||
var reader = new FileReader();
|
||||
reader.readAsDataURL(e.target.files[0]);
|
||||
reader.onload = data => {
|
||||
images.push(data.target.result);
|
||||
};
|
||||
|
||||
imgElement.value = "";
|
||||
img_number++;
|
||||
});
|
||||
|
||||
function addPara() {
|
||||
var para = document.createElement("textarea");
|
||||
para.setAttribute("class", "para");
|
||||
para.setAttribute("id", `para_${blog_para_number}`);
|
||||
para.setAttribute("spellcheck", false);
|
||||
para.setAttribute("rows", 1);
|
||||
para.setAttribute(
|
||||
"onkeyup",
|
||||
`addRow(event), addDataToOriginalPara('${blog_para_number}')`
|
||||
);
|
||||
para.setAttribute("required", true);
|
||||
para.setAttribute("placeholder", "What's on your Mind?");
|
||||
var remove = document.createElement("div");
|
||||
remove.setAttribute("class", "remove");
|
||||
remove.setAttribute(
|
||||
"onclick",
|
||||
`remove(event,'para_${blog_para_number}', null)`
|
||||
);
|
||||
remove.innerHTML = '<i class="fas fa-times"></i> Remove';
|
||||
var originalPara = document.createElement("p");
|
||||
originalPara.setAttribute("id", `para_${blog_para_number}_original`);
|
||||
document.querySelector("#blog").appendChild(para);
|
||||
document.querySelector("#blog").appendChild(remove);
|
||||
document.querySelector("#originalContent").appendChild(originalPara);
|
||||
blog_para_number++;
|
||||
}
|
||||
|
||||
function submitthisform() {
|
||||
document.querySelector("#content").value = document.querySelector(
|
||||
"#originalContent"
|
||||
).innerHTML;
|
||||
document.querySelector("#images").value = JSON.stringify(images);
|
||||
document.querySelector("#form").submit();
|
||||
}
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
Binary file not shown.
|
@ -1,299 +1,299 @@
|
|||
@import url("https://fonts.googleapis.com/css?family=Poppins");
|
||||
@import url("https://fonts.googleapis.com/css?family=Questrial");
|
||||
|
||||
@font-face {
|
||||
font-family: "Circular";
|
||||
src: url("./font/Circular.otf");
|
||||
}
|
||||
|
||||
body {
|
||||
margin: 0%;
|
||||
padding: 0%;
|
||||
width: 100vw;
|
||||
max-width: 100vw;
|
||||
overflow-x: hidden;
|
||||
align-items: center;
|
||||
font-family: "Poppins", sans-serif;
|
||||
background: rgb(250, 250, 250) !important;
|
||||
will-change: auto;
|
||||
}
|
||||
|
||||
header {
|
||||
width: 90vw;
|
||||
padding: 4vh 5vw;
|
||||
font-weight: bold;
|
||||
background: rgb(255, 255, 255);
|
||||
font-size: 32px;
|
||||
}
|
||||
|
||||
header b {
|
||||
font-family: "Circular", sans-serif;
|
||||
}
|
||||
|
||||
header a {
|
||||
font-size: 16px;
|
||||
margin: 1.8vh 0px;
|
||||
margin-left: 4vw;
|
||||
color: #000;
|
||||
text-decoration: none;
|
||||
transition: 0.4s ease-in-out;
|
||||
}
|
||||
|
||||
header a:hover {
|
||||
color: #bebebe;
|
||||
}
|
||||
|
||||
form {
|
||||
width: 90vw;
|
||||
padding: 2vh 5vw;
|
||||
}
|
||||
|
||||
form .button {
|
||||
margin: 2vh 0px;
|
||||
}
|
||||
|
||||
.input {
|
||||
margin: 1.5vh 0px !important;
|
||||
}
|
||||
|
||||
.label {
|
||||
display: inline-block !important;
|
||||
margin-right: 25px;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
button {
|
||||
transition: 0.4s ease-in-out !important;
|
||||
}
|
||||
|
||||
button:hover {
|
||||
color: #fff;
|
||||
background: #000 !important;
|
||||
}
|
||||
|
||||
.-size-small {
|
||||
margin-right: 1vw !important;
|
||||
}
|
||||
|
||||
#top_image {
|
||||
width: 100vw;
|
||||
height: 50vh;
|
||||
position: absolute;
|
||||
top: 14vh;
|
||||
left: 0;
|
||||
background: linear-gradient(0deg, rgb(250, 250, 250), rgb(200, 200, 200));
|
||||
background-size: cover !important;
|
||||
background-repeat: no-repeat !important;
|
||||
z-index: 1;
|
||||
text-align: right;
|
||||
}
|
||||
|
||||
#top_image i {
|
||||
font-size: 20px;
|
||||
position: absolute;
|
||||
z-index: 5;
|
||||
top: 4vh;
|
||||
right: 5vw;
|
||||
padding: 15px 15px;
|
||||
background: #ffffff;
|
||||
color: rgb(0, 0, 0);
|
||||
border-radius: 50%;
|
||||
}
|
||||
|
||||
#top_image i:hover {
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
#profile_blog {
|
||||
width: 60vw;
|
||||
margin: 0px 20vw;
|
||||
margin-top: 42vh !important;
|
||||
text-align: left;
|
||||
z-index: 1;
|
||||
transition: 0.4s ease-in-out;
|
||||
z-index: 2;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
#profile_img_blog {
|
||||
border-radius: 50%;
|
||||
width: 90px;
|
||||
height: 90px;
|
||||
background-size: cover !important;
|
||||
background-repeat: no-repeat;
|
||||
}
|
||||
|
||||
#username_blog {
|
||||
font-size: 18px;
|
||||
color: #000;
|
||||
font-family: "Poppins", sans-serif;
|
||||
font-weight: bold;
|
||||
padding-left: 0px;
|
||||
}
|
||||
|
||||
#username_blog span {
|
||||
font-size: 24px;
|
||||
font-family: "Questrial", sans-serif !important;
|
||||
}
|
||||
|
||||
#username_blog b {
|
||||
font-size: 12px;
|
||||
font-family: "Poppins", sans-serif;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
#blog-display {
|
||||
width: 60vw;
|
||||
margin: 3vh 20vw;
|
||||
text-align: left;
|
||||
z-index: 1;
|
||||
transition: 0.4s ease-in-out;
|
||||
z-index: 2;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
#blog_title {
|
||||
font-size: 50px;
|
||||
color: #000;
|
||||
font-weight: bold;
|
||||
font-family: "Questrial", sans-serif;
|
||||
background: transparent;
|
||||
border: 0px;
|
||||
width: 100%;
|
||||
resize: none;
|
||||
height: auto;
|
||||
overflow-y: hidden;
|
||||
}
|
||||
|
||||
#blog_sub_title {
|
||||
font-size: 36px;
|
||||
color: rgb(100, 100, 100);
|
||||
font-weight: bold;
|
||||
font-family: "Questrial", sans-serif;
|
||||
background: transparent;
|
||||
border: 0px;
|
||||
width: 100%;
|
||||
resize: none;
|
||||
height: auto;
|
||||
overflow-y: hidden;
|
||||
}
|
||||
|
||||
#blog_sub_title::placeholder {
|
||||
color: rgb(100, 100, 100);
|
||||
}
|
||||
|
||||
#blog-display h2 {
|
||||
color: var(--blog-gray-color);
|
||||
}
|
||||
|
||||
#blog-display {
|
||||
padding: 1vh 0px;
|
||||
font-family: "Questrial", sans-serif;
|
||||
}
|
||||
|
||||
.div_for_buttons {
|
||||
margin-top: 5vh;
|
||||
}
|
||||
|
||||
.para {
|
||||
font-size: 17px;
|
||||
line-height: 25px;
|
||||
word-spacing: 1.2px;
|
||||
margin: 5vh 0px;
|
||||
background: transparent;
|
||||
border: 0px;
|
||||
width: 100%;
|
||||
font-family: "Questrial", sans-serif;
|
||||
resize: none;
|
||||
height: auto;
|
||||
overflow-y: hidden;
|
||||
}
|
||||
|
||||
.para span {
|
||||
padding: 2px 4px;
|
||||
background: #000;
|
||||
color: #fff !important;
|
||||
}
|
||||
|
||||
#blog {
|
||||
margin-top: 2vh;
|
||||
}
|
||||
|
||||
#blog img {
|
||||
width: 100%;
|
||||
margin: 2vh 0px;
|
||||
border-radius: 5px;
|
||||
border: 1px solid rgb(0, 0, 0, 0.08);
|
||||
}
|
||||
|
||||
.remove {
|
||||
margin-bottom: 2vh 0px;
|
||||
font-weight: bold;
|
||||
transition: 0.4s ease-in-out;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.remove i {
|
||||
font-size: 14px;
|
||||
margin-right: 3px;
|
||||
}
|
||||
|
||||
.remove:hover {
|
||||
cursor: pointer;
|
||||
color: rgb(255, 70, 70);
|
||||
}
|
||||
|
||||
@media (max-width: 800px) {
|
||||
#blog-display {
|
||||
width: 90vw;
|
||||
margin: 0px 5vw;
|
||||
text-align: left;
|
||||
margin-top: 0vh;
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
#profile_blog {
|
||||
width: 90vw;
|
||||
margin: 0px 5vw;
|
||||
}
|
||||
|
||||
#profile_img_blog {
|
||||
width: 70px;
|
||||
height: 70px;
|
||||
}
|
||||
|
||||
#blog img {
|
||||
margin: 1vh 0px !important;
|
||||
}
|
||||
|
||||
#blog p {
|
||||
margin: 2vh 0px;
|
||||
}
|
||||
}
|
||||
|
||||
::selection {
|
||||
color: #fff;
|
||||
background: #000;
|
||||
}
|
||||
|
||||
::-webkit-scrollbar {
|
||||
width: 5px;
|
||||
height: 5px;
|
||||
}
|
||||
|
||||
::-webkit-scrollbar-track {
|
||||
background: #fff;
|
||||
}
|
||||
|
||||
::-webkit-scrollbar-thumb {
|
||||
background: #000;
|
||||
}
|
||||
|
||||
input,
|
||||
textarea:focus {
|
||||
outline: none;
|
||||
}
|
||||
|
||||
::placeholder {
|
||||
color: #000;
|
||||
}
|
||||
@import url("https://fonts.googleapis.com/css?family=Poppins");
|
||||
@import url("https://fonts.googleapis.com/css?family=Questrial");
|
||||
|
||||
@font-face {
|
||||
font-family: "Circular";
|
||||
src: url("./font/Circular.otf");
|
||||
}
|
||||
|
||||
body {
|
||||
margin: 0%;
|
||||
padding: 0%;
|
||||
width: 100vw;
|
||||
max-width: 100vw;
|
||||
overflow-x: hidden;
|
||||
align-items: center;
|
||||
font-family: "Poppins", sans-serif;
|
||||
background: rgb(250, 250, 250) !important;
|
||||
will-change: auto;
|
||||
}
|
||||
|
||||
header {
|
||||
width: 90vw;
|
||||
padding: 4vh 5vw;
|
||||
font-weight: bold;
|
||||
background: rgb(255, 255, 255);
|
||||
font-size: 32px;
|
||||
}
|
||||
|
||||
header b {
|
||||
font-family: "Circular", sans-serif;
|
||||
}
|
||||
|
||||
header a {
|
||||
font-size: 16px;
|
||||
margin: 1.8vh 0px;
|
||||
margin-left: 4vw;
|
||||
color: #000;
|
||||
text-decoration: none;
|
||||
transition: 0.4s ease-in-out;
|
||||
}
|
||||
|
||||
header a:hover {
|
||||
color: #bebebe;
|
||||
}
|
||||
|
||||
form {
|
||||
width: 90vw;
|
||||
padding: 2vh 5vw;
|
||||
}
|
||||
|
||||
form .button {
|
||||
margin: 2vh 0px;
|
||||
}
|
||||
|
||||
.input {
|
||||
margin: 1.5vh 0px !important;
|
||||
}
|
||||
|
||||
.label {
|
||||
display: inline-block !important;
|
||||
margin-right: 25px;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
button {
|
||||
transition: 0.4s ease-in-out !important;
|
||||
}
|
||||
|
||||
button:hover {
|
||||
color: #fff;
|
||||
background: #000 !important;
|
||||
}
|
||||
|
||||
.-size-small {
|
||||
margin-right: 1vw !important;
|
||||
}
|
||||
|
||||
#top_image {
|
||||
width: 100vw;
|
||||
height: 50vh;
|
||||
position: absolute;
|
||||
top: 14vh;
|
||||
left: 0;
|
||||
background: linear-gradient(0deg, rgb(250, 250, 250), rgb(200, 200, 200));
|
||||
background-size: cover !important;
|
||||
background-repeat: no-repeat !important;
|
||||
z-index: 1;
|
||||
text-align: right;
|
||||
}
|
||||
|
||||
#top_image i {
|
||||
font-size: 20px;
|
||||
position: absolute;
|
||||
z-index: 5;
|
||||
top: 4vh;
|
||||
right: 5vw;
|
||||
padding: 15px 15px;
|
||||
background: #ffffff;
|
||||
color: rgb(0, 0, 0);
|
||||
border-radius: 50%;
|
||||
}
|
||||
|
||||
#top_image i:hover {
|
||||
cursor: pointer;
|
||||
}
|
||||
|
||||
#profile_blog {
|
||||
width: 60vw;
|
||||
margin: 0px 20vw;
|
||||
margin-top: 42vh !important;
|
||||
text-align: left;
|
||||
z-index: 1;
|
||||
transition: 0.4s ease-in-out;
|
||||
z-index: 2;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
#profile_img_blog {
|
||||
border-radius: 50%;
|
||||
width: 90px;
|
||||
height: 90px;
|
||||
background-size: cover !important;
|
||||
background-repeat: no-repeat;
|
||||
}
|
||||
|
||||
#username_blog {
|
||||
font-size: 18px;
|
||||
color: #000;
|
||||
font-family: "Poppins", sans-serif;
|
||||
font-weight: bold;
|
||||
padding-left: 0px;
|
||||
}
|
||||
|
||||
#username_blog span {
|
||||
font-size: 24px;
|
||||
font-family: "Questrial", sans-serif !important;
|
||||
}
|
||||
|
||||
#username_blog b {
|
||||
font-size: 12px;
|
||||
font-family: "Poppins", sans-serif;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
#blog-display {
|
||||
width: 60vw;
|
||||
margin: 3vh 20vw;
|
||||
text-align: left;
|
||||
z-index: 1;
|
||||
transition: 0.4s ease-in-out;
|
||||
z-index: 2;
|
||||
position: relative;
|
||||
}
|
||||
|
||||
#blog_title {
|
||||
font-size: 50px;
|
||||
color: #000;
|
||||
font-weight: bold;
|
||||
font-family: "Questrial", sans-serif;
|
||||
background: transparent;
|
||||
border: 0px;
|
||||
width: 100%;
|
||||
resize: none;
|
||||
height: auto;
|
||||
overflow-y: hidden;
|
||||
}
|
||||
|
||||
#blog_sub_title {
|
||||
font-size: 36px;
|
||||
color: rgb(100, 100, 100);
|
||||
font-weight: bold;
|
||||
font-family: "Questrial", sans-serif;
|
||||
background: transparent;
|
||||
border: 0px;
|
||||
width: 100%;
|
||||
resize: none;
|
||||
height: auto;
|
||||
overflow-y: hidden;
|
||||
}
|
||||
|
||||
#blog_sub_title::placeholder {
|
||||
color: rgb(100, 100, 100);
|
||||
}
|
||||
|
||||
#blog-display h2 {
|
||||
color: var(--blog-gray-color);
|
||||
}
|
||||
|
||||
#blog-display {
|
||||
padding: 1vh 0px;
|
||||
font-family: "Questrial", sans-serif;
|
||||
}
|
||||
|
||||
.div_for_buttons {
|
||||
margin-top: 5vh;
|
||||
}
|
||||
|
||||
.para {
|
||||
font-size: 17px;
|
||||
line-height: 25px;
|
||||
word-spacing: 1.2px;
|
||||
margin: 5vh 0px;
|
||||
background: transparent;
|
||||
border: 0px;
|
||||
width: 100%;
|
||||
font-family: "Questrial", sans-serif;
|
||||
resize: none;
|
||||
height: auto;
|
||||
overflow-y: hidden;
|
||||
}
|
||||
|
||||
.para span {
|
||||
padding: 2px 4px;
|
||||
background: #000;
|
||||
color: #fff !important;
|
||||
}
|
||||
|
||||
#blog {
|
||||
margin-top: 2vh;
|
||||
}
|
||||
|
||||
#blog img {
|
||||
width: 100%;
|
||||
margin: 2vh 0px;
|
||||
border-radius: 5px;
|
||||
border: 1px solid rgb(0, 0, 0, 0.08);
|
||||
}
|
||||
|
||||
.remove {
|
||||
margin-bottom: 2vh 0px;
|
||||
font-weight: bold;
|
||||
transition: 0.4s ease-in-out;
|
||||
font-size: 16px;
|
||||
}
|
||||
|
||||
.remove i {
|
||||
font-size: 14px;
|
||||
margin-right: 3px;
|
||||
}
|
||||
|
||||
.remove:hover {
|
||||
cursor: pointer;
|
||||
color: rgb(255, 70, 70);
|
||||
}
|
||||
|
||||
@media (max-width: 800px) {
|
||||
#blog-display {
|
||||
width: 90vw;
|
||||
margin: 0px 5vw;
|
||||
text-align: left;
|
||||
margin-top: 0vh;
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
#profile_blog {
|
||||
width: 90vw;
|
||||
margin: 0px 5vw;
|
||||
}
|
||||
|
||||
#profile_img_blog {
|
||||
width: 70px;
|
||||
height: 70px;
|
||||
}
|
||||
|
||||
#blog img {
|
||||
margin: 1vh 0px !important;
|
||||
}
|
||||
|
||||
#blog p {
|
||||
margin: 2vh 0px;
|
||||
}
|
||||
}
|
||||
|
||||
::selection {
|
||||
color: #fff;
|
||||
background: #000;
|
||||
}
|
||||
|
||||
::-webkit-scrollbar {
|
||||
width: 5px;
|
||||
height: 5px;
|
||||
}
|
||||
|
||||
::-webkit-scrollbar-track {
|
||||
background: #fff;
|
||||
}
|
||||
|
||||
::-webkit-scrollbar-thumb {
|
||||
background: #000;
|
||||
}
|
||||
|
||||
input,
|
||||
textarea:focus {
|
||||
outline: none;
|
||||
}
|
||||
|
||||
::placeholder {
|
||||
color: #000;
|
||||
}
|
||||
|
|
306
views/index.ejs
306
views/index.ejs
|
@ -1,153 +1,153 @@
|
|||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
|
||||
<title>Gitfolio UI</title>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.7.0/animate.min.css"
|
||||
/>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://use.fontawesome.com/releases/v5.7.1/css/all.css"
|
||||
integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr"
|
||||
crossorigin="anonymous"
|
||||
/>
|
||||
<link rel="stylesheet" type="text/css" href="./css/index.css" />
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdn.jsdelivr.net/gh/zeva-ui/zeva/dist/css/zeva.min.css"
|
||||
/>
|
||||
</head>
|
||||
<body class="body-light">
|
||||
<header>
|
||||
<b>gitfolio</b>
|
||||
<a href="/blog" style="float: right">New Blog </a>
|
||||
<a href="/update" style="float: right">Update</a>
|
||||
<a href="/" style="float: right">Home</a>
|
||||
</header>
|
||||
<form method="post" action="build">
|
||||
<h3>Build or Edit Portfolio</h3>
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="username"
|
||||
id="username"
|
||||
name="username"
|
||||
required
|
||||
/><br />
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="background"
|
||||
name="background"
|
||||
id="background"
|
||||
/>
|
||||
<h3>Sort By :</h3>
|
||||
<label class="label"
|
||||
>Star
|
||||
<input type="radio" name="sort" value="star" />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
|
||||
<label class="label"
|
||||
>Created
|
||||
<input type="radio" name="sort" value="created" checked />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
|
||||
<label class="label"
|
||||
>Updated
|
||||
<input type="radio" name="sort" value="updated" />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
|
||||
<label class="label"
|
||||
>Pushed
|
||||
<input type="radio" name="sort" value="pushed" />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
|
||||
<label class="label"
|
||||
>Full Name
|
||||
<input type="radio" name="sort" value="full_name" />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
|
||||
<h3>Order By :</h3>
|
||||
<label class="label"
|
||||
>Asc
|
||||
<input type="radio" name="order" value="asc" checked />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
<label class="label"
|
||||
>Desc
|
||||
<input type="radio" name="order" value="desc" />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
<br /><br />
|
||||
<label class="label"
|
||||
>Use Dark Theme
|
||||
<input type="checkbox" id="theme" name="theme" />
|
||||
<span class="checkbox"></span>
|
||||
</label>
|
||||
<label class="label"
|
||||
>Include Forks
|
||||
<input type="checkbox" id="fork" name="fork" value="true" />
|
||||
<span class="checkbox"></span>
|
||||
</label>
|
||||
<label class="label"
|
||||
>Include Socials
|
||||
<input type="checkbox" id="socials" name="socials" />
|
||||
<span class="checkbox"></span>
|
||||
</label>
|
||||
<div style="display: none" id="input_for_socials">
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="twitter username"
|
||||
id="twitter"
|
||||
name="twitter"
|
||||
/><br />
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="medium username"
|
||||
id="medium"
|
||||
name="medium"
|
||||
/><br />
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="dribbble username"
|
||||
id="dribbble"
|
||||
name="dribbble"
|
||||
/><br />
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="linkedin username"
|
||||
id="linkedin"
|
||||
name="linkedin"
|
||||
/>
|
||||
</div>
|
||||
<br /><br />
|
||||
<button type="submit" class="button" id="build">Build</button>
|
||||
</form>
|
||||
<script
|
||||
type="text/javascript"
|
||||
src="https://cdn.jsdelivr.net/gh/zeva-ui/zeva/dist/js/index.min.js"
|
||||
></script>
|
||||
<script type="text/javascript">
|
||||
document.querySelector("#socials").addEventListener("change", event => {
|
||||
if (event.target.checked) {
|
||||
document.querySelector("#input_for_socials").style.display = "block";
|
||||
} else {
|
||||
document.querySelector("#input_for_socials").style.display = "none";
|
||||
}
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<meta http-equiv="X-UA-Compatible" content="ie=edge" />
|
||||
<title>Gitfolio UI</title>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdnjs.cloudflare.com/ajax/libs/animate.css/3.7.0/animate.min.css"
|
||||
/>
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://use.fontawesome.com/releases/v5.7.1/css/all.css"
|
||||
integrity="sha384-fnmOCqbTlWIlj8LyTjo7mOUStjsKC4pOpQbqyi7RrhN7udi9RwhKkMHpvLbHG9Sr"
|
||||
crossorigin="anonymous"
|
||||
/>
|
||||
<link rel="stylesheet" type="text/css" href="./css/index.css" />
|
||||
<link
|
||||
rel="stylesheet"
|
||||
href="https://cdn.jsdelivr.net/gh/zeva-ui/zeva/dist/css/zeva.min.css"
|
||||
/>
|
||||
</head>
|
||||
<body class="body-light">
|
||||
<header>
|
||||
<b>gitfolio</b>
|
||||
<a href="/blog" style="float: right">New Blog </a>
|
||||
<a href="/update" style="float: right">Update</a>
|
||||
<a href="/" style="float: right">Home</a>
|
||||
</header>
|
||||
<form method="post" action="build">
|
||||
<h3>Build or Edit Portfolio</h3>
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="username"
|
||||
id="username"
|
||||
name="username"
|
||||
required
|
||||
/><br />
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="background"
|
||||
name="background"
|
||||
id="background"
|
||||
/>
|
||||
<h3>Sort By :</h3>
|
||||
<label class="label"
|
||||
>Star
|
||||
<input type="radio" name="sort" value="star" />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
|
||||
<label class="label"
|
||||
>Created
|
||||
<input type="radio" name="sort" value="created" checked />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
|
||||
<label class="label"
|
||||
>Updated
|
||||
<input type="radio" name="sort" value="updated" />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
|
||||
<label class="label"
|
||||
>Pushed
|
||||
<input type="radio" name="sort" value="pushed" />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
|
||||
<label class="label"
|
||||
>Full Name
|
||||
<input type="radio" name="sort" value="full_name" />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
|
||||
<h3>Order By :</h3>
|
||||
<label class="label"
|
||||
>Asc
|
||||
<input type="radio" name="order" value="asc" checked />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
<label class="label"
|
||||
>Desc
|
||||
<input type="radio" name="order" value="desc" />
|
||||
<span class="radio"></span>
|
||||
</label>
|
||||
<br /><br />
|
||||
<label class="label"
|
||||
>Use Dark Theme
|
||||
<input type="checkbox" id="theme" name="theme" />
|
||||
<span class="checkbox"></span>
|
||||
</label>
|
||||
<label class="label"
|
||||
>Include Forks
|
||||
<input type="checkbox" id="fork" name="fork" value="true" />
|
||||
<span class="checkbox"></span>
|
||||
</label>
|
||||
<label class="label"
|
||||
>Include Socials
|
||||
<input type="checkbox" id="socials" name="socials" />
|
||||
<span class="checkbox"></span>
|
||||
</label>
|
||||
<div style="display: none" id="input_for_socials">
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="twitter username"
|
||||
id="twitter"
|
||||
name="twitter"
|
||||
/><br />
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="medium username"
|
||||
id="medium"
|
||||
name="medium"
|
||||
/><br />
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="dribbble username"
|
||||
id="dribbble"
|
||||
name="dribbble"
|
||||
/><br />
|
||||
<input
|
||||
type="text"
|
||||
class="input h-weight-bold"
|
||||
placeholder="linkedin username"
|
||||
id="linkedin"
|
||||
name="linkedin"
|
||||
/>
|
||||
</div>
|
||||
<br /><br />
|
||||
<button type="submit" class="button" id="build">Build</button>
|
||||
</form>
|
||||
<script
|
||||
type="text/javascript"
|
||||
src="https://cdn.jsdelivr.net/gh/zeva-ui/zeva/dist/js/index.min.js"
|
||||
></script>
|
||||
<script type="text/javascript">
|
||||
document.querySelector("#socials").addEventListener("change", event => {
|
||||
if (event.target.checked) {
|
||||
document.querySelector("#input_for_socials").style.display = "block";
|
||||
} else {
|
||||
document.querySelector("#input_for_socials").style.display = "none";
|
||||
}
|
||||
});
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
Loading…
Reference in a new issue