Implemented navigation

This commit is contained in:
Michael Mayer 2018-08-03 15:17:13 +02:00
parent fcddb5ddfe
commit 04fb039ab6
20 changed files with 331 additions and 90 deletions

1
.gitignore vendored
View file

@ -36,5 +36,6 @@ Thumbs.db
.settings
.swp
.tmp
/photos/
/vendor/
node_modules/

View file

@ -1,4 +1,4 @@
darktable-cli: /Applications/darktable.app/Contents/MacOS/darktable-cli
darktable-cli: /usr/bin/darktable-cli
originals-path: photos/originals
thumbnails-path: photos/thumbnails
import-path: photos/import

View file

@ -1,50 +1,50 @@
#alerts {
position: fixed;
z-index: 1051;
left: 20%;
top: 10px;
right: 20%;
top: 50px;
left: 0;
right: 0;
height: auto;
display: block;
opacity: 0.7;
}
#alerts .success {
background-color: #71D774;
background-color: #c8e5ff;
}
#alerts .success:after {
}
#alerts .error {
background-color: #FF5A5A;
background-color: #ffcaca;
}
#alerts .error:before {
}
#alerts .warning {
background-color: #FCBD39;
background-color: #ffedc1;
}
#alerts .warning:before {
}
#alerts .info {
color: #49AFF5;
background-color: #49AFF5;
background-color: #feffb8;
}
#alerts .alert {
color: #FFF;
color: #333;
display: block;
left: 0;
right: 0;
min-height: 14px;
padding: 8px 10px 8px 10px;
font-size: 14px;
min-height: 13px;
padding: 4px 10px 4px 10px;
font-size: 13px;
font-weight: bold;
opacity: 1;
border-radius: 0;
border-radius: 0px;
margin: 1px 0 0 0;
}

View file

@ -19,36 +19,66 @@
background-color: rgba(0,0,0,0.2);
}
body {
background: #333333;
color: rgba(255,255,255,0.9);
}
main {
margin: 10px 20px;
}
/*
nav {
background-color: #616161;
padding: 0;
margin: 0;
}
nav a:hover {
text-decoration: none !important;
color: rgba(255, 255, 255, .87) !important;
main div.page {
padding: 2rem;
}
nav a {
font-size: 14px;
font-weight: bold !important;
text-transform: uppercase;
display: inline-block;
text-align: center;
width: 120px;
background: #616161;
padding: 10px;
text-decoration: none;
border-bottom: 3px solid #616161;
color: rgba(255, 255, 255, .54) !important;
.navbar {
padding: 3px 2rem 3px 2rem;
background: black !important;
}
nav a.router-link-active {
font-weight: bold !important;
border-bottom: 3px solid #E64A19;
color: rgba(255, 255, 255, .87) !important;
}*/
.navbar .nav-item-photos .nav-link.active,
.navbar .nav-item-photos .nav-link:hover {
color: #c8e5ff;
}
main div.page-photos {
border-top: 2px solid #c8e5ff;
}
.navbar .nav-item-albums .nav-link.active,
.navbar .nav-item-albums .nav-link:hover {
color: #c4ffcb;
}
main div.page-albums {
border-top: 2px solid #c4ffcb;
}
.navbar .nav-item-import .nav-link.active,
.navbar .nav-item-import .nav-link:hover {
color: #feffb8;
}
main div.page-import {
border-top: 2px solid #feffb8;
}
.navbar .nav-item-export .nav-link.active,
.navbar .nav-item-export .nav-link:hover {
color: #ffedc1;
}
main div.page-export {
border-top: 2px solid #ffedc1;
}
.navbar .nav-item-settings .nav-link.active,
.navbar .nav-item-settings .nav-link:hover {
color: #f5c5c5;
}
main div.page-settings {
border-top: 2px solid #f5c5c5;
}

View file

@ -15,7 +15,9 @@
"axios-mock-adapter": "^1.8.1",
"chart.js": "^2.5.0",
"font-awesome": "^4.7.0",
"justified-gallery": "^0.1.0",
"vue": "^2.4.4",
"vue-justified-layout": "^0.1.0",
"vue-router": "^2.7.0",
"vue-template-compiler": "^2.4.4"
},
@ -31,16 +33,14 @@
"babel-preset-es2015": "^6.24.1",
"babel-preset-stage-2": "^6.22.0",
"babel-register": "^6.22.0",
"bootstrap-vue": "^2.0.0-rc.11",
"bootstrap": "^4.1.3",
"bootstrap-vue": "^2.0.0-rc.11",
"chai": "^3.5.0",
"chalk": "^1.1.3",
"connect-history-api-fallback": "^1.3.0",
"copy-webpack-plugin": "^4.0.1",
"cross-env": "^3.1.4",
"css-loader": "^0.28.11",
"node-sass": "^4.9.2",
"sass-loader": "^7.0.3",
"eslint": "^3.14.1",
"eslint-config-standard": "^6.2.1",
"eslint-friendly-formatter": "^2.0.7",
@ -65,11 +65,13 @@
"karma-webpack": "^2.0.3",
"lodash": "^4.17.4",
"mocha": "^3.3.0",
"node-sass": "^4.9.2",
"optimize-css-assets-webpack-plugin": "^1.3.0",
"ora": "^1.1.0",
"phantomjs-prebuilt": "^2.1.14",
"pluralize": "^4.0.0",
"pubsub-js": "^1.5.6",
"sass-loader": "^7.0.3",
"style-loader": "^0.16.1",
"svg-url-loader": "^2.0.2",
"url-loader": "^0.5.8",
@ -91,4 +93,4 @@
"last 2 versions",
"not ie <= 8"
]
}
}

View file

@ -0,0 +1,36 @@
<template>
<div class="page page-albums">
<h1 class="md-display-1">Albums</h1>
<p class="md-subheading">
A user-friendly tool for importing, filtering and archiving large amounts of JPEG and RAW files
</p>
</div>
</template>
<script>
export default {
name: 'browse',
data() {
return {
};
},
methods: {
}
};
</script>
<style scoped>
h1, h2 {
font-weight: normal;
}
ul {
list-style-type: none;
padding: 0;
}
li {
display: inline-block;
margin: 0 10px;
}
</style>

View file

@ -0,0 +1,36 @@
<template>
<div class="page page-export">
<h1 class="md-display-1">Export</h1>
<p class="md-subheading">
A user-friendly tool for importing, filtering and archiving large amounts of JPEG and RAW files
</p>
</div>
</template>
<script>
export default {
name: 'browse',
data() {
return {
};
},
methods: {
}
};
</script>
<style scoped>
h1, h2 {
font-weight: normal;
}
ul {
list-style-type: none;
padding: 0;
}
li {
display: inline-block;
margin: 0 10px;
}
</style>

View file

@ -0,0 +1,36 @@
<template>
<div class="page page-import">
<h1>Import</h1>
<p class="md-subheading">
A user-friendly tool for importing, filtering and archiving large amounts of JPEG and RAW files
</p>
</div>
</template>
<script>
export default {
name: 'import',
data() {
return {
};
},
methods: {
}
};
</script>
<style scoped>
h1, h2 {
font-weight: normal;
}
ul {
list-style-type: none;
padding: 0;
}
li {
display: inline-block;
margin: 0 10px;
}
</style>

View file

@ -1,7 +1,5 @@
<template>
<div class="dashboard">
<div class="page page-photos">
<h1 class="md-display-1">Welcome to PhotoPrism</h1>
<p class="md-subheading">
A user-friendly tool for importing, filtering and archiving large amounts of JPEG and RAW files
@ -11,25 +9,12 @@
<script>
export default {
name: 'dashboard',
name: 'photos',
data() {
return {
msg: 'Welcome to PhotoPrism',
username: this.$session.getFullName(),
};
},
methods: {
open() {
this.$refs.snackbar.open();
},
showNotification() {
this.$alert.success('Yeah wuwuwu');
},
logout() {
this.$session.logout();
},
}
};
</script>

View file

@ -0,0 +1,52 @@
<template>
<div class="page page-settings">
<h1 class="md-display-1">Settings</h1>
<p class="md-subheading">
</p>
<button v-on:click="showSuccess()">Show Success</button>
<button v-on:click="showInfo()">Show Info</button>
<button v-on:click="showError()">Show Error</button>
<button v-on:click="showWarning()">Show Warning</button>
</div>
</template>
<script>
export default {
name: 'dashboard',
data() {
return {
};
},
methods: {
showSuccess() {
this.$alert.success('Action successfully completed');
},
showInfo() {
this.$alert.info('This is an info');
},
showError() {
this.$alert.error('An error has occurred - please check logs');
},
showWarning() {
this.$alert.warning('This is a warning');
},
}
};
</script>
<style scoped>
h1, h2 {
font-weight: normal;
}
ul {
list-style-type: none;
padding: 0;
}
li {
display: inline-block;
margin: 0 10px;
}
</style>

View file

@ -1,7 +1,15 @@
import Welcome from 'app/pages/welcome.vue';
import Photos from 'app/pages/photos.vue';
import Albums from 'app/pages/albums.vue';
import Import from 'app/pages/Import.vue';
import Export from 'app/pages/Export.vue';
import Settings from 'app/pages/settings.vue';
export default [
{ path: '/', redirect: '/welcome' },
{ path: '/welcome', component: Welcome },
{ path: '*', redirect: '/welcome' },
{ path: '/', redirect: '/photos' },
{ path: '/photos', component: Photos },
{ path: '/albums', component: Albums },
{ path: '/import', component: Import },
{ path: '/export', component: Export },
{ path: '/settings', component: Settings },
{ path: '*', redirect: '/photos' },
];

View file

@ -4,14 +4,16 @@
<b-navbar-toggle target="nav_collapse"></b-navbar-toggle>
<b-navbar-brand href="#">PhotoPrism</b-navbar-brand>
<b-navbar-brand href="/"><img src="/assets/img/logo.png" alt="PhotoPrism"></b-navbar-brand>
<b-collapse is-nav id="nav_collapse">
<b-navbar-nav>
<b-nav-item href="#">Browse</b-nav-item>
<b-nav-item href="#">Import</b-nav-item>
<b-nav-item href="#">Export</b-nav-item>
<b-nav-item to="/photos" class="nav-item-photos">Photos</b-nav-item>
<b-nav-item to="/albums" class="nav-item-albums">Albums</b-nav-item>
<b-nav-item to="/import" class="nav-item-import">Import</b-nav-item>
<b-nav-item to="/export" class="nav-item-export">Export</b-nav-item>
<b-nav-item to="/settings" class="nav-item-settings">Settings</b-nav-item>
</b-navbar-nav>
<!-- Right aligned nav items -->
@ -22,21 +24,6 @@
<b-button size="sm" class="my-2 my-sm-0" type="submit">Search</b-button>
</b-nav-form>
<b-nav-item-dropdown text="Lang" right>
<b-dropdown-item href="#">EN</b-dropdown-item>
<b-dropdown-item href="#">ES</b-dropdown-item>
<b-dropdown-item href="#">RU</b-dropdown-item>
<b-dropdown-item href="#">FA</b-dropdown-item>
</b-nav-item-dropdown>
<b-nav-item-dropdown right>
<!-- Using button-content slot -->
<template slot="button-content">
User
</template>
<b-dropdown-item href="#">Profile</b-dropdown-item>
<b-dropdown-item href="#">Signout</b-dropdown-item>
</b-nav-item-dropdown>
</b-navbar-nav>
</b-collapse>

View file

@ -3917,6 +3917,10 @@ istanbul-lib-instrument@^1.4.2:
istanbul-lib-coverage "^1.2.0"
semver "^5.3.0"
jquery@^3.1.0:
version "3.3.1"
resolved "https://registry.yarnpkg.com/jquery/-/jquery-3.3.1.tgz#958ce29e81c9790f31be7792df5d4d95fc57fbca"
js-base64@^2.1.8, js-base64@^2.1.9:
version "2.4.8"
resolved "https://registry.yarnpkg.com/js-base64/-/js-base64-2.4.8.tgz#57a9b130888f956834aa40c5b165ba59c758f033"
@ -4021,6 +4025,18 @@ jsprim@^1.2.2:
json-schema "0.2.3"
verror "1.10.0"
justified-gallery@^0.1.0:
version "0.1.0"
resolved "https://registry.yarnpkg.com/justified-gallery/-/justified-gallery-0.1.0.tgz#b4b861accd5641e47d223e649ea493bf05dc2794"
dependencies:
jquery "^3.1.0"
justified-layout@^2.1.1:
version "2.1.1"
resolved "https://registry.yarnpkg.com/justified-layout/-/justified-layout-2.1.1.tgz#22da0c296d3a95b7a3d5fb7f48dbbe0e6539b7f1"
dependencies:
merge "1.2.0"
karma-chrome-launcher@^2.1.1:
version "2.2.0"
resolved "https://registry.yarnpkg.com/karma-chrome-launcher/-/karma-chrome-launcher-2.2.0.tgz#cf1b9d07136cc18fe239327d24654c3dbc368acf"
@ -4427,6 +4443,10 @@ merge-descriptors@1.0.1:
version "1.0.1"
resolved "https://registry.yarnpkg.com/merge-descriptors/-/merge-descriptors-1.0.1.tgz#b00aaa556dd8b44568150ec9d1b953f3f90cbb61"
merge@1.2.0:
version "1.2.0"
resolved "https://registry.yarnpkg.com/merge/-/merge-1.2.0.tgz#7531e39d4949c281a66b8c5a6e0265e8b05894da"
methods@~1.1.2:
version "1.1.2"
resolved "https://registry.yarnpkg.com/methods/-/methods-1.1.2.tgz#5529a4d67654134edcc5266656835b0f851afcee"
@ -7057,6 +7077,13 @@ vue-hot-reload-api@^2.0.11:
version "2.3.0"
resolved "https://registry.yarnpkg.com/vue-hot-reload-api/-/vue-hot-reload-api-2.3.0.tgz#97976142405d13d8efae154749e88c4e358cf926"
vue-justified-layout@^0.1.0:
version "0.1.0"
resolved "https://registry.yarnpkg.com/vue-justified-layout/-/vue-justified-layout-0.1.0.tgz#f26b606614719697aeff98f26b68795b926ae013"
dependencies:
justified-layout "^2.1.1"
vue "^2.4.4"
vue-loader@^11.1.4:
version "11.3.4"
resolved "https://registry.yarnpkg.com/vue-loader/-/vue-loader-11.3.4.tgz#65e10a44ce092d906e14bbc72981dec99eb090d2"

View file

@ -34,7 +34,13 @@ func (i *Indexer) GetImageTags(jpeg *MediaFile) (result []Tag) {
for _, tag := range tags {
if tag.Probability > 0.2 {
result = append(result, Tag{Label: tag.Label})
var tagModel Tag
if res := i.db.First(&tagModel, "label = ?", tag.Label); res.Error != nil {
tagModel.Label = tag.Label
}
result = append(result, tagModel)
}
}
}

View file

@ -6,9 +6,11 @@ import (
type Photo struct {
gorm.Model
Title string
Description string `gorm:"type:text;"`
CanonicalName string
PerceptualHash string
Tags []Tag `gorm:"many2many:photo_tags;"`
Tags []Tag `gorm:"many2many:photo_tags;"`
Files []File
Albums []Album `gorm:"many2many:album_photos;"`
Author string

Binary file not shown.

Before

Width:  |  Height:  |  Size: 1.4 KiB

After

Width:  |  Height:  |  Size: 1.1 KiB

BIN
server/assets/img/logo.png Normal file

Binary file not shown.

After

Width:  |  Height:  |  Size: 5.3 KiB

View file

@ -4,6 +4,7 @@ import (
"github.com/gin-gonic/gin"
"fmt"
"net/http"
"github.com/photoprism/photoprism"
)
func Start(address string, port int) {
@ -14,11 +15,31 @@ func Start(address string, port int) {
router.StaticFile("/favicon.ico", "./server/assets/favicon.ico")
router.StaticFile("/robots.txt", "./server/assets/robots.txt")
// JSON-REST API Version 1
v1 := router.Group("/v1")
{
v1.GET("/photos", func(c *gin.Context) {
photos := []*photoprism.Photo{ &photoprism.Photo{Title: "Bar"}, &photoprism.Photo{ Title: "Foo" } }
c.JSON(http.StatusOK, photos)
})
v1.GET("/albums", func(c *gin.Context) {
c.JSON(http.StatusOK, gin.H{"status": "ok"})
})
v1.GET("/tags", func(c *gin.Context) {
c.JSON(http.StatusOK, gin.H{"status": "ok"})
})
}
router.Static("/assets", "./server/assets")
router.NoRoute(func(c *gin.Context) {
c.HTML(http.StatusOK, "index.tmpl", gin.H{
"title": "PhotoPrism",
"debug": true,
})
})

View file

@ -1,20 +1,32 @@
<!doctype html>
<html class="no-js" lang="">
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1">
<title></title>
<title>{{ .title }}</title>
<meta name="description" content="">
<meta name="author" content="">
<meta name="viewport" content="width=device-width, initial-scale=1">
<link rel="apple-touch-icon" href="apple-touch-icon.png">
<link rel="apple-touch-icon" href="/apple-touch-icon.png">
<link rel="shortcut icon" href="/favicon.ico">
<link rel="stylesheet" href="/assets/build/app.css">
<script>
window.appConfig = {
appName: "{{ .title }}",
appVersion: "1.0.0",
debug: {{ .debug }}
};
</script>
</head>
<body>
<!--[if lt IE 8]>
<p class="browserupgrade">You are using an <strong>outdated</strong> browser. Please <a href="http://browsehappy.com/">upgrade your browser</a> to improve your experience.</p>
<![endif]-->
<div id="alerts"></div>
<div id="app" class="container">
<div class="loading">
<img src="/assets/img/ajax-loader.gif">

2
tag.go
View file

@ -6,5 +6,5 @@ import (
type Tag struct {
gorm.Model
Label string
Label string `gorm:"type:varchar(100);unique_index"`
}