Merge pull request #3022 from wallabag/webpack

Adds Webpack support and remove Grunt
This commit is contained in:
Thomas Citharel 2017-05-09 11:43:48 +02:00 committed by GitHub
commit b28c5430ef
202 changed files with 8810 additions and 132082 deletions

5
.babelrc Normal file
View file

@ -0,0 +1,5 @@
{
"presets": [
["env", {"modules": false}]
]
}

1
.gitignore vendored
View file

@ -27,6 +27,7 @@ web/bundles/*
!web/bundles/wallabagcore !web/bundles/wallabagcore
/web/assets/images/* /web/assets/images/*
!web/assets/images/.gitkeep !web/assets/images/.gitkeep
web/bundles/wallabagcore/*.dev.js
# Build # Build
/app/build /app/build

View file

@ -20,7 +20,6 @@ cache:
- vendor - vendor
- $HOME/.composer/cache - $HOME/.composer/cache
- node_modules - node_modules
- $HOME/.cache/bower
- $HOME/.npm - $HOME/.npm
php: php:
@ -59,9 +58,9 @@ before_script:
- if [[ $DB = pgsql ]]; then psql -c 'create database wallabag_test;' -U postgres; fi; - if [[ $DB = pgsql ]]; then psql -c 'create database wallabag_test;' -U postgres; fi;
install: install:
- if [[ $ASSETS = build ]]; then source ~/.nvm/nvm.sh && nvm install 6.7; fi; - if [[ $ASSETS = build ]]; then source ~/.nvm/nvm.sh && nvm install 6.10; fi;
- if [[ $ASSETS = build ]]; then npm install -g npm@latest; fi; - if [[ $ASSETS = build ]]; then npm install -g yarn@latest; fi;
- if [[ $ASSETS = build ]]; then npm install; fi; - if [[ $ASSETS = build ]]; then yarn install; fi;
before_install: before_install:
- if [[ $TRAVIS_REPO_SLUG = wallabag/wallabag ]]; then cp .composer-auth.json ~/.composer/auth.json; fi; - if [[ $TRAVIS_REPO_SLUG = wallabag/wallabag ]]; then cp .composer-auth.json ~/.composer/auth.json; fi;
@ -74,4 +73,4 @@ script:
- if [[ $VALIDATE_TRANSLATION_FILE = run ]]; then php bin/console lint:yaml src/Wallabag/CoreBundle/Resources/translations -v ; fi; - if [[ $VALIDATE_TRANSLATION_FILE = run ]]; then php bin/console lint:yaml src/Wallabag/CoreBundle/Resources/translations -v ; fi;
- if [[ $VALIDATE_TRANSLATION_FILE = run ]]; then php bin/console lint:yaml app/Resources/CraueConfigBundle/translations -v ; fi; - if [[ $VALIDATE_TRANSLATION_FILE = run ]]; then php bin/console lint:yaml app/Resources/CraueConfigBundle/translations -v ; fi;
- if [[ $VALIDATE_TRANSLATION_FILE = run ]]; then php bin/console lint:yaml src/Wallabag/UserBundle/Resources/translations -v ; fi; - if [[ $VALIDATE_TRANSLATION_FILE = run ]]; then php bin/console lint:yaml src/Wallabag/UserBundle/Resources/translations -v ; fi;
- if [[ $ASSETS = build ]]; then ./node_modules/grunt-cli/bin/grunt tests; fi; - if [[ $ASSETS = build ]]; then yarn run build:prod; fi;

View file

@ -1,230 +0,0 @@
module.exports = function (grunt) {
require('load-grunt-tasks')(grunt);
grunt.initConfig({
appDir: 'app/Resources/static',
buildDir: 'app/Resources/build',
modulesDir: 'node_modules',
releaseDir: 'web/bundles/wallabagcore',
postcss: {
material: {
options: {
processors: [
require('pixrem')(),
require('autoprefixer')({ browsers: 'last 2 versions' }),
require('cssnano')(),
],
},
src: '<%= buildDir %>/material.css',
dest: '<%= releaseDir %>/themes/material/css/style.min.css',
},
baggy: {
options: {
processors: [
require('pixrem')(),
require('autoprefixer')({ browsers: 'last 2 versions' }),
require('cssnano')(),
],
},
src: '<%= buildDir %>/baggy.css',
dest: '<%= releaseDir %>/themes/baggy/css/style.min.css',
},
},
concat: {
options: {
separator: ';',
},
cssMaterial: {
src: [
'node_modules/materialize-css/bin/materialize.css',
'<%= appDir %>/themes/material/css/*.css',
],
dest: '<%= buildDir %>/material.css',
},
cssBaggy: {
src: [
'<%= appDir %>/themes/baggy/css/*.css',
],
dest: '<%= buildDir %>/baggy.css',
},
},
browserify: {
dist: {
files: {
'<%= buildDir %>/material.browser.js': ['<%= appDir %>/themes/material/js/init.js'],
'<%= buildDir %>/baggy.browser.js': ['<%= appDir %>/themes/baggy/js/init.js']
}
},
options: {
sourceType: "module",
transform: [
["babelify", {
presets: ["es2015"]
}], ["browserify-shim", {
"jquery": {
"exports": "$"
},
"materialize": "materialize",
"jquery-ui": {
"depends": "jquery",
"exports": null
}
}]
],
browserifyOptions: {
browser: {
"jQuery": "./node_modules/jquery/dist/jquery.js",
"jquery.tinydot": "./node_modules/jquery.tinydot/src/jquery.tinydot.js",
"jquery.ui": "./node_modules/jquery-ui-browserify/dist/jquery-ui.js"
}
}
}
},
uglify: {
material: {
files: {
'<%= releaseDir %>/themes/material/js/material.min.js':
['<%= buildDir %>/material.browser.js'],
}
},
baggy: {
files: {
'<%= releaseDir %>/themes/baggy/js/baggy.min.js':
['<%= buildDir %>/baggy.browser.js'],
}
},
},
copy: {
pickerjs: {
expand: true,
cwd: '<%= modulesDir %>/pickadate/lib',
src: 'picker.js',
dest: '<%= buildDir %>',
},
annotator: {
expand: true,
cwd: '<%= modulesDir %>/annotator/pkg',
src: 'annotator.min.js',
dest: '<%= buildDir %>/themes/_global/js/',
},
baggyfonts: {
files: [
{
expand: true,
cwd: '<%= modulesDir %>/icomoon-free-npm/Font',
src: 'IcoMoon-Free.ttf',
dest: '<%= releaseDir %>/themes/baggy/fonts/',
},
{
expand: true,
cwd: '<%= modulesDir %>/ptsans-npm-webfont/fonts',
src: 'ptsansbold.woff',
dest: '<%= releaseDir %>/themes/baggy/fonts/',
},
{
expand: true,
cwd: '<%= modulesDir %>/material-design-icons-iconfont/dist/fonts/',
src: ['MaterialIcons-Regular.eot', 'MaterialIcons-Regular.woff2', 'MaterialIcons-Regular.woff', 'MaterialIcons-Regular.ttf'],
dest: '<%= releaseDir %>/themes/baggy/fonts/',
},
],
},
materialfonts: {
files: [
{
expand: true,
overwrite: true,
cwd: '<%= modulesDir %>/icomoon-free-npm/Font',
src: 'IcoMoon-Free.ttf',
dest: '<%= releaseDir %>/themes/material/fonts',
},
{
expand: true,
overwrite: true,
cwd: '<%= modulesDir %>/roboto-fontface/fonts/Roboto',
src: '*',
dest: '<%= releaseDir %>/themes/material/font/roboto',
},
{
expand: true,
overwrite: true,
cwd: '<%= modulesDir %>/material-design-icons-iconfont/dist/fonts/',
src: ['MaterialIcons-Regular.eot', 'MaterialIcons-Regular.woff2', 'MaterialIcons-Regular.woff', 'MaterialIcons-Regular.ttf'],
dest: '<%= releaseDir %>/themes/material/fonts/',
},
],
},
},
symlink: {
pics: {
files: [
{
expand: true,
overwrite: true,
cwd: '<%= appDir %>/themes/_global/',
src: 'img',
dest: '<%= releaseDir %>/themes/_global/',
},
],
},
},
clean: {
css: {
src: ['<%= buildDir %>/**/*.css'],
},
js: {
src: ['<%= buildDir %>/**/*.js', '<%= buildDir %>/**/*.map'],
},
all: {
src: ['./<%= buildDir %>'],
},
release: {
src: ['./<%= releaseDir %>/*'],
}
},
eslint: {
target: ['<%= appDir %>/themes/material/js/init.js', '<%= appDir %>/themes/baggy/js/init.js']
},
stylelint: {
target: ['<%= appDir %>/themes/material/css/*.css', '<%= appDir %>/themes/baggy/css/*.css']
},
watch: {
files: ['<%= appDir %>/**/*.css', '<%= appDir %>/**/*.js'],
tasks: ['css', 'js']
}
});
grunt.registerTask(
'fonts',
'Install fonts',
['copy:baggyfonts', 'copy:materialfonts']
);
grunt.registerTask(
'js',
'Build and install js files',
['clean:js', 'copy:pickerjs', 'browserify', 'uglify']
);
grunt.registerTask(
'default',
'Build and install everything',
['clean', 'copy:pickerjs', 'concat', 'browserify', 'uglify', 'postcss', 'copy', 'symlink']
);
grunt.registerTask(
'css',
'Compiles the stylesheets.',
['clean:css', 'concat:cssMaterial', 'concat:cssBaggy', 'postcss']
);
grunt.registerTask(
'tests',
'Test css and js style conformity',
['eslint', 'stylelint', 'default']
),
grunt.loadNpmTasks('grunt-contrib-watch');
};

View file

@ -71,5 +71,14 @@ class AppKernel extends Kernel
public function registerContainerConfiguration(LoaderInterface $loader) public function registerContainerConfiguration(LoaderInterface $loader)
{ {
$loader->load($this->getRootDir().'/config/config_'.$this->getEnvironment().'.yml'); $loader->load($this->getRootDir().'/config/config_'.$this->getEnvironment().'.yml');
$loader->load(function ($container) {
if ($container->getParameter('use_webpack_dev_server')) {
$container->loadFromExtension('framework', [
'assets' => [
'base_url' => 'http://localhost:8080/',
],
]);
}
});
} }
} }

View file

@ -0,0 +1,13 @@
/* Rules for sizing the icon. */
.material-icons.md-18 { font-size: 18px; }
.material-icons.md-24 { font-size: 24px; }
.material-icons.md-36 { font-size: 36px; }
.material-icons.md-48 { font-size: 48px; }
/* Rules for using icons as black on a light background. */
.material-icons.md-dark { color: rgba(0, 0, 0, 0.54); }
.material-icons.md-dark.md-inactive { color: rgba(0, 0, 0, 0.26); }
/* Rules for using icons as white on a dark background. */
.material-icons.md-light { color: rgba(255, 255, 255, 1); }
.material-icons.md-light.md-inactive { color: rgba(255, 255, 255, 0.3); }

View file

@ -0,0 +1,334 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:xlink="http://www.w3.org/1999/xlink"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
width="800"
height="770"
id="svg4004"
version="1.1"
inkscape:version="0.48.4 r9939"
sodipodi:docname="New document 11">
<defs
id="defs4006" />
<sodipodi:namedview
id="base"
pagecolor="#000"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageopacity="0.0"
inkscape:pageshadow="2"
inkscape:zoom="0.7"
inkscape:cx="359.23155"
inkscape:cy="349.10374"
inkscape:document-units="px"
inkscape:current-layer="layer1"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:window-width="1631"
inkscape:window-height="1026"
inkscape:window-x="49"
inkscape:window-y="24"
inkscape:window-maximized="1" />
<metadata
id="metadata4009">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<g
inkscape:label="Layer 1"
inkscape:groupmode="layer"
id="layer1"
transform="translate(21.42857,-101.6479)">
<image
y="101.6479"
x="-21.42857"
id="image4071"
xlink:href="data:image/png;base64,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
"
height="770"
width="800" />
<path
style="fill:#FFF"
d="m 482.45517,806.8979 c -21.575,-30.1125 -55.23748,-77.12866 -74.80551,-104.48035 -19.98598,-27.9359 -36.2457,-49.73896 -37.10125,-49.75 -0.87914,-0.0113 -32.32337,42.25713 -74.37706,99.98035 -40.06973,55 -73.18741,100 -73.59485,100 -1.1396,0 -144.46068,-100.94983 -144.829571,-102.01235 -0.178476,-0.51406 32.221521,-48.07611 72.000001,-105.69344 39.77847,-57.61732 72.3245,-105.66675 72.3245,-106.77649 0,-1.78957 -12.89022,-6.31508 -114,-40.0232 -62.7,-20.90302 -114.613999,-38.24519 -115.364443,-38.53815 -1.043816,-0.4075 4.925559,-20.38013 25.402971,-84.99452 14.722078,-46.45402 27.100359,-84.84113 27.507293,-85.3047 0.406933,-0.46357 54.900599,16.97442 121.097029,38.75107 66.19643,21.77666 120.91108,39.59345 121.5881,39.59285 0.67702,-5.9e-4 1.44284,-1.01357 1.70181,-2.25107 0.25898,-1.2375 0.83006,-57.6 1.26906,-125.25 0.439,-67.65 1.16224,-123.5625 1.6072,-124.25 0.63709,-0.98436 19.23178,-1.24675 87.5,-1.23469 47.68004,0.008 87.18776,0.34593 87.79493,0.75 0.76529,0.50931 2.07325,37.70117 4.26357,121.23469 3.5965,137.16189 3.67401,139 5.86123,139 0.84816,0 53.3106,-17.56056 116.58321,-39.02347 63.2726,-21.46291 115.34958,-38.67541 115.72663,-38.25 1.27822,1.44219 53.1745,170.39371 52.53554,171.03267 -0.34901,0.34901 -53.15524,18.43347 -117.34717,40.18769 -88.30357,29.92548 -116.78951,39.96068 -117.02855,41.22754 -0.17651,0.93542 30.19001,46.31568 68.80279,102.8201 38.0153,55.63011 68.97925,101.56053 68.80877,102.06759 -0.39157,1.16463 -142.63129,105.93788 -143.82081,105.93788 -0.48298,0 -18.53042,-24.6375 -40.10542,-54.75 z"
id="path4093"
inkscape:connector-curvature="0" />
</g>
</svg>

After

Width:  |  Height:  |  Size: 23 KiB

View file

@ -0,0 +1,52 @@
/* jQuery */
import $ from 'jquery';
/* Annotations */
import annotator from 'annotator';
/* Fonts */
import 'material-design-icons-iconfont/dist/material-design-icons.css';
import 'lato-font/css/lato-font.css';
import './global.scss';
/* Shortcuts*/
import './js/shortcuts/entry';
import './js/shortcuts/main';
import { savePercent, retrievePercent } from './js/tools';
/* ==========================================================================
Annotations & Remember position
========================================================================== */
$(document).ready(() => {
if ($('article').length) {
const app = new annotator.App();
app.include(annotator.ui.main, {
element: document.querySelector('article'),
});
const x = JSON.parse($('#annotationroutes').html());
app.include(annotator.storage.http, x);
app.start().then(() => {
app.annotations.load({ entry: x.entryId });
});
$(window).scroll(() => {
const scrollTop = $(window).scrollTop();
const docHeight = $(document).height();
const scrollPercent = (scrollTop) / (docHeight);
const scrollPercentRounded = Math.round(scrollPercent * 100) / 100;
savePercent(x.entryId, scrollPercentRounded);
});
retrievePercent(x.entryId);
$(window).resize(() => {
retrievePercent(x.entryId);
});
}
});

View file

@ -31,25 +31,4 @@ function retrievePercent(id) {
return true; return true;
} }
function initFilters() { export { savePercent, retrievePercent };
// no display if filters not available
if ($('div').is('#filters')) {
$('#button_filters').show();
$('.js-filters-action').sideNav({ edge: 'right' });
$('#clear_form_filters').on('click', () => {
$('#filters input').val('');
$('#filters :checked').removeAttr('checked');
return false;
});
}
}
function initExport() {
// no display if export not available
if ($('div').is('#export')) {
$('#button_export').show();
$('.js-export-action').sideNav({ edge: 'right' });
}
}
export { savePercent, retrievePercent, initFilters, initExport };

View file

@ -0,0 +1,165 @@
#article {
width: 70%;
margin-bottom: 3em;
text-align: justify;
.tags {
margin-bottom: 1em;
}
i {
font-style: normal;
}
h1 {
text-align: left;
}
h2::after {
content: none;
}
h2,
h3,
h4 {
text-transform: none;
}
}
blockquote {
border: 1px solid #999;
background-color: #fff;
padding: 1em;
margin: 0;
}
.topPosF {
position: fixed;
right: 20%;
bottom: 2em;
font-size: 1.5em;
}
#article_toolbar {
margin-bottom: 1em;
li {
display: inline-block;
margin: 3px auto;
}
a {
background-color: #000;
padding: 0.3em 0.5em 0.2em;
color: #fff;
text-decoration: none;
&:hover,
&:focus {
background-color: #999;
}
}
}
#nav-btn-add-tag {
cursor: pointer;
}
.shaarli::before {
content: "*";
}
.return {
text-decoration: none;
margin-top: 1em;
display: block;
}
.return::before {
margin-right: 0.5em;
}
.notags {
font-style: italic;
color: #999;
}
.icon-rss {
background-color: #000;
color: #fff;
padding: 0.2em 0.5em;
&::before {
position: relative;
top: 2px;
}
}
.list-tags {
li {
margin-bottom: 0.5em;
}
.icon-rss:hover,
.icon-rss:focus {
background-color: #fff;
color: #000;
text-decoration: none;
}
a {
text-decoration: none;
&:hover,
&:focus {
text-decoration: underline;
}
}
}
pre code {
font-family: "Courier New", Courier, monospace;
}
#filters {
position: fixed;
width: 20%;
height: 100%;
top: 0;
right: 0;
background-color: #fff;
padding: 30px 30px 15px 15px;
border-left: 1px #333 solid;
z-index: 12;
min-width: 300px;
form .filter-group {
margin: 5px;
}
}
#download-form {
position: fixed;
width: 10%;
height: 100%;
top: 0;
right: 0;
background-color: #fff;
padding: 30px 30px 15px 15px;
border-left: 1px #333 solid;
z-index: 12;
min-width: 200px;
li {
display: block;
padding: 0.5em 2em 0.5em 1em;
color: #fff;
position: relative;
text-transform: uppercase;
text-decoration: none;
font-weight: 400;
font-family: PT Sans, sans-serif;
transition: all 0.5s ease;
}
}

View file

@ -1,6 +0,0 @@
@font-face {
font-family: "PT Sans";
font-style: normal;
font-weight: 700;
src: local("PT Sans Bold"), local("PTSans-Bold"), url("../fonts/ptsansbold.woff") format("woff");
}

View file

@ -0,0 +1,263 @@
::selection {
color: #fff;
background-color: #000;
}
.desktopHide {
display: none;
}
.logo {
position: fixed;
z-index: 20;
top: 0.4em;
left: 0.6em;
}
h2,
h3,
h4 {
font-family: "PT Sans", sans-serif;
text-transform: uppercase;
}
p,
li,
label {
color: #666;
}
a {
color: #000;
font-weight: bold;
&.nostyle {
text-decoration: none;
}
&:hover,
&:focus {
text-decoration: none;
}
}
form fieldset {
border: 0;
padding: 0;
margin: 0;
}
form input[type="text"],
form input[type="number"],
select,
form input[type="password"],
form input[type="url"],
form input[type="email"] {
border: 1px solid #999;
padding: 0.5em 1em;
min-width: 12em;
color: #666;
}
@media screen and (-webkit-min-device-pixel-ratio: 0) {
select {
-webkit-appearance: none;
border-radius: 0;
background: #fff url("../../_global/img/bg-select.png") no-repeat right center;
}
}
.inline {
.row {
display: inline-block;
margin-right: 0.5em;
}
label {
min-width: 6em;
}
}
fieldset label {
display: inline-block;
min-width: 12.5em;
color: #666;
}
label {
margin-right: 0.5em;
}
form .row {
margin-bottom: 0.5em;
}
form button,
input[type="submit"] {
cursor: pointer;
background-color: #000;
color: #fff;
padding: 0.5em 1em;
display: inline-block;
border: 1px solid #000;
}
form button:hover,
form button:focus,
input[type="submit"]:hover,
input[type="submit"]:focus {
background-color: #fff;
color: #000;
-webkit-transition: all 0.5s ease;
-moz-transition: all 0.5s ease;
-ms-transition: all 0.5s ease;
-o-transition: all 0.5s ease;
transition: all 0.5s ease;
}
#bookmarklet {
cursor: move;
}
h2::after {
content: "";
height: 4px;
width: 20%;
background-color: #000;
display: block;
}
.links {
padding: 0;
margin: 0;
li {
list-style: none;
margin: 0;
padding: 0;
}
}
#links {
position: fixed;
top: 0;
width: 10em;
left: 0;
text-align: right;
background-color: #333;
padding-top: 9.5em;
height: 100%;
box-shadow: inset -4px 0 20px rgba(0, 0, 0, 0.6);
z-index: 15;
> li > a {
display: block;
padding: 0.5em 2em 0.5em 1em;
color: #fff;
position: relative;
text-transform: uppercase;
text-decoration: none;
font-weight: normal;
font-family: "PT Sans", sans-serif;
transition: all 0.5s ease;
&:hover,
&:focus {
background-color: #999;
color: #000;
}
}
.current::after {
content: "";
width: 0;
height: 0;
position: absolute;
border: 10px solid transparent;
border-right-color: #eee;
right: 0;
top: 50%;
margin-top: -10px;
}
li:last-child {
position: fixed;
bottom: 1em;
width: 10em;
a::before {
font-size: 1.2em;
position: relative;
top: 2px;
}
}
}
#main {
margin-left: 12em;
position: relative;
z-index: 10;
padding-right: 5%;
padding-bottom: 1em;
}
#sort {
padding: 0;
list-style-type: none;
opacity: 0.5;
display: inline-block;
li {
display: inline;
font-size: 0.9em;
& + li {
margin-left: 10px;
}
}
a {
padding: 2px 2px 0;
vertical-align: middle;
}
img {
vertical-align: baseline;
:hover {
cursor: pointer;
}
}
}
#display-mode {
float: right;
margin-top: 10px;
margin-bottom: 10px;
opacity: 0.5;
}
#listmode {
width: 16px;
display: inline-block;
text-decoration: none;
&.tablemode {
background: url("../../_global/img/table.png") no-repeat bottom;
}
.listmode {
background: url("../../_global/img/list.png") no-repeat bottom;
}
}
#warning_message {
position: fixed;
background-color: #ff6347;
z-index: 1000;
bottom: 0;
left: 0;
width: 100%;
color: #000;
}

View file

@ -0,0 +1,13 @@
/* Style */
@import 'guide';
@import 'layout';
@import 'article';
@import 'pictos';
@import 'login';
@import 'save';
@import 'messages';
/* Tools */
@import 'media_queries';
@import 'print';
@import 'ratatouille';

View file

@ -0,0 +1,300 @@
#content {
margin-top: 2em;
min-height: 30em;
}
footer {
text-align: right;
position: relative;
bottom: 0;
right: 5em;
color: #999;
font-size: 0.8em;
font-style: italic;
z-index: 20;
a {
color: #999;
font-weight: normal;
}
}
.list-entries {
letter-spacing: -5px;
}
.listmode.entry {
width: 100%;
height: inherit;
}
.card-entry-tags {
max-height: 2em;
overflow-y: hidden;
padding: 0;
margin: 0;
}
.card-entry-tags li,
.card-entry-tags span {
display: inline-block;
margin: 0 5px;
padding: 5px 12px;
background-color: rgba(0, 0, 0, 0.6);
border-radius: 3px;
max-height: 2em;
overflow: hidden;
text-overflow: ellipsis;
}
.card-entry-tags a,
.card-entry-labels a {
text-decoration: none;
font-weight: normal;
color: #fff;
}
.nav-panel-add-tag {
margin-top: 10px;
}
.list-entries + .results {
margin-bottom: 2em;
}
.reading-time,
.created-at {
color: #999;
font-style: italic;
font-weight: normal;
font-size: 0.9em;
}
.estimatedTime small {
position: relative;
top: -1px;
}
.entry {
background-color: #fff;
letter-spacing: normal;
box-shadow: 0 3px 7px rgba(0, 0, 0, 0.3);
display: inline-block;
width: 32%;
margin-bottom: 1.5em;
vertical-align: top;
margin-right: 1%;
position: relative;
overflow: hidden;
padding: 1.5em 0 3em;
height: 440px;
img.preview {
width: 100%;
object-fit: cover;
height: 100%;
}
&::before {
content: "";
width: 0;
height: 0;
border: 10px solid transparent;
border-bottom-color: #000;
position: absolute;
bottom: 0.7em;
z-index: 10;
right: 1.5em;
transition: all 0.5s ease;
}
&::after {
content: "";
position: absolute;
height: 7px;
width: 100%;
bottom: 0;
left: 0;
background-color: #000;
transition: all 0.5s ease;
}
&:hover {
box-shadow: 0 3px 10px rgba(0, 0, 0, 1);
&::after {
height: 40px;
}
&::before {
bottom: 2.3em;
}
h2 a {
color: #666;
}
.tools {
bottom: 0;
}
}
h2 {
text-transform: none;
margin-bottom: 0;
line-height: 1.2;
margin-left: 5px;
}
&::after {
content: none;
}
a {
display: block;
text-decoration: none;
color: #000;
word-wrap: break-word;
transition: all 0.5s ease;
}
p {
color: #666;
font-size: 0.9em;
line-height: 1.7;
margin: 5px 5px auto;
}
h2 a::first-letter {
text-transform: uppercase;
}
.tools {
position: absolute;
bottom: -40px;
left: 0;
background: #000;
width: 100%;
z-index: 10;
padding-right: 0.5em;
text-align: right;
transition: all 0.5s ease;
a {
color: #666;
text-decoration: none;
display: block;
padding: 0.4em;
&:hover {
color: #fff;
}
}
li {
display: inline-block;
margin-top: 10px;
}
li:first-child {
float: left;
font-size: 0.9em;
max-width: calc(100% - 40px * 4);
text-overflow: ellipsis;
overflow: hidden;
white-space: nowrap;
max-height: 2em;
margin-left: 10px;
}
}
.card-entry-labels {
position: absolute;
top: 100px;
left: -1em;
z-index: 90;
max-width: 50%;
padding-left: 0;
li {
margin: 10px 10px 10px auto;
padding: 5px 12px 5px 25px;
background-color: rgba(0, 0, 0, 0.6);
border-radius: 0 3px 3px 0;
color: #fff;
cursor: default;
max-height: 2em;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
a {
color: #fff;
}
}
}
}
.entry:nth-child(3n+1) {
margin-left: 0;
}
.results {
letter-spacing: -5px;
padding: 0 0 0.5em;
> * {
display: inline-block;
vertical-align: top;
letter-spacing: normal;
width: 50%;
text-align: right;
}
}
div.pagination ul {
text-align: right;
}
.nb-results {
text-align: left;
font-style: italic;
color: #999;
display: inline-flex;
}
div.pagination ul {
a {
color: #999;
text-decoration: none;
&:hover,
&:focus {
text-decoration: underline;
}
}
> * {
display: inline-block;
margin-left: 0.5em;
}
.prev.disabled,
.next.disabled {
display: none;
}
.current {
height: 25px;
padding: 4px 8px;
border: 1px solid #d5d5d5;
text-decoration: none;
font-weight: bold;
color: #000;
background-color: #ccc;
}
}
.hide {
display: none;
}

View file

@ -0,0 +1,26 @@
.login {
background-color: #333;
#main {
padding: 0;
margin: 0;
}
form {
background-color: #fff;
padding: 1.5em;
box-shadow: 0 1px 8px rgba(0, 0, 0, 0.9);
width: 20em;
position: absolute;
top: 8em;
left: 50%;
margin-left: -10em;
}
.logo {
position: absolute;
top: 2em;
left: 50%;
margin-left: -55px;
}
}

View file

@ -0,0 +1,172 @@
@media screen and (max-width: 1050px) {
.entry {
width: 49%;
}
.entry:nth-child(3n+1) {
margin-left: 1.5%;
}
.entry:nth-child(2n+1) {
margin-left: 0;
}
}
@media screen and (max-width: 900px) {
#article {
width: 80%;
}
.topPosF {
right: 2.5em;
}
}
@media screen and (max-width: 700px) {
.entry {
width: 100%;
margin-left: 0;
}
#display-mode {
display: none;
}
}
@media screen and (max-height: 770px) {
.menu.users,
.menu.internal,
.menu.developer {
display: none;
}
}
@media screen and (max-width: 500px) {
.entry {
width: 100%;
margin-left: 0;
}
body > header {
background-color: #333;
position: fixed;
top: 0;
width: 100%;
height: 3em;
z-index: 11;
}
#links li:last-child {
position: static;
width: auto;
}
#links li:last-child a::before {
content: none;
}
.logo {
width: 1.25em;
height: 1.25em;
left: 0;
top: 0;
}
.login > header {
position: static;
}
.login form {
width: 100%;
position: static;
margin-left: 0;
}
.login .logo {
height: auto;
top: 0.5em;
width: 75px;
margin-left: -37.5px;
}
.desktopHide {
display: block;
position: fixed;
z-index: 20;
top: 0;
right: 0;
border: 0;
width: 2.5em;
height: 2.5em;
cursor: pointer;
background-color: #999;
font-size: 1.2em;
}
.desktopHide:hover,
.desktopHide:focus {
background-color: #fff;
}
#links {
display: none;
width: 100%;
height: auto;
padding-top: 3em;
}
#links.menu--open {
display: block;
}
footer {
position: static;
margin-right: 3em;
}
#main {
margin-left: 1.5em;
padding-right: 1.5em;
position: static;
margin-top: 3em;
}
.card-entry-labels {
display: none;
}
#article_toolbar .topPosF {
display: none;
}
#article {
width: 100%;
}
#article h1 {
font-size: 1.5em;
}
#article_toolbar a {
padding: 0.3em 0.4em 0.2em;
}
#display-mode {
display: none;
}
.popup-form,
#bagit-form,
#search-form {
left: 0;
width: 100%;
border-left: none;
}
.popup-form form,
#bagit-form form,
#search-form form {
width: 100%;
}
}

View file

@ -1,19 +0,0 @@
.messages.error.install {
border: 1px solid #c42608;
color: #c00 !important;
background: #fff0ef;
text-align: left;
}
.messages.notice.install {
border: 1px solid #ebcd41;
color: #000;
background: #fffcd3;
text-align: left;
}
.messages.success.install {
border: 1px solid #6dc70c;
background: #e0fbcc !important;
text-align: left;
}

View file

@ -0,0 +1,50 @@
/* ==========================================================================
Messages
========================================================================== */
.messages {
text-align: left;
width: 60%;
margin: auto 17%;
> * {
display: inline-block;
}
.install {
text-align: left;
&.error {
border: 1px solid #c42608;
color: #c00 !important;
background: #fff0ef;
}
&.notice {
border: 1px solid #ebcd41;
color: #000;
background: #fffcd3;
}
&.success {
border: 1px solid #6dc70c;
background: #e0fbcc !important;
}
}
}
.warning {
font-weight: bold;
display: block;
width: 100%;
}
.more-info {
font-size: 0.85em;
line-height: 1.5;
color: #aaa;
a {
color: #aaa;
}
}

View file

@ -0,0 +1,210 @@
/* ==========================================================================
Pictos
========================================================================== */
@font-face {
font-family: icomoon;
src: url('~icomoon-free-npm/Font/IcoMoon-Free.ttf');
font-weight: normal;
font-style: normal;
}
.material-icons {
font-family: 'Material Icons';
font-weight: normal;
font-style: normal;
font-size: 1em; /* Preferred icon size */
width: 1em;
height: 1em;
display: inline-block;
line-height: 1;
text-transform: none;
letter-spacing: normal;
word-wrap: normal;
white-space: nowrap;
direction: ltr;
/* Support for all WebKit browsers. */
-webkit-font-smoothing: antialiased;
/* Support for Safari and Chrome. */
text-rendering: optimizeLegibility;
/* Support for Firefox. */
-moz-osx-font-smoothing: grayscale;
/* Support for IE. */
font-feature-settings: 'liga';
.md-18 { font-size: 18px; }
.md-24 { font-size: 24px; }
.md-36 { font-size: 36px; }
.md-48 { font-size: 48px; }
.vertical-align-middle {
vertical-align: middle !important;
}
}
.icon span,
.icon-image span {
position: absolute;
top: -9999px;
}
[class^="icon-"]::before,
[class*=" icon-"]::before {
font-family: icomoon;
speak: none;
font-style: normal;
font-weight: normal;
font-variant: normal;
text-transform: none;
line-height: 1;
/* Enable Ligatures ================ */
letter-spacing: 0;
-webkit-font-feature-settings: "liga";
-moz-font-feature-settings: "liga=1";
-moz-font-feature-settings: "liga";
-ms-font-feature-settings: "liga" 1;
-o-font-feature-settings: "liga";
font-feature-settings: "liga";
/* Better Font Rendering =========== */
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
}
.icon-flattr::before {
content: "\ead4";
}
.icon-mail::before {
content: "\ea86";
}
.icon-up-open::before {
content: "\e80b";
}
.icon-star::before {
content: "\e9d9";
}
.icon-check::before {
content: "\ea10";
}
.icon-link::before {
content: "\e9cb";
}
.icon-reply::before {
content: "\e806";
}
.icon-menu::before {
content: "\e9bd";
}
.icon-clock::before {
content: "\e803";
}
.icon-twitter::before {
content: "\ea96";
}
.icon-down-open::before {
content: "\e809";
}
.icon-trash::before {
content: "\e9ac";
}
.icon-delete::before {
content: "\ea0d";
}
.icon-power::before {
content: "\ea14";
}
.icon-arrow-up-thick::before {
content: "\ea3a";
}
.icon-rss::before {
content: "\e808";
}
.icon-print::before {
content: "\e954";
}
.icon-reload::before {
content: "\ea2e";
}
.icon-price-tags::before {
content: "\e936";
}
.icon-eye::before {
content: "\e9ce";
}
.icon-no-eye::before {
content: "\e9d1";
}
.icon-calendar::before {
content: "\e953";
}
.icon-time::before {
content: "\e952";
}
/* .icon-image class, for image-based icons
========================================================================== */
.icon-image {
background: no-repeat center/80%;
padding-right: 1em !important;
padding-left: 1em !important;
}
/* Carrot (http://carrot.org) */
.icon-image--carrot {
background-image: url("../../_global/img/icons/carrot-icon--white.png");
}
/* Diaspora */
.icon-image--diaspora {
background-image: url("../../_global/img/icons/Diaspora-asterisk.svg");
}
/* Unmark.it */
.icon-image--unmark {
background-image: url("../../_global/img/icons/unmark-icon--black.png");
}
/* shaarli */
.icon-image--shaarli {
background-image: url("../../_global/img/icons/shaarli.png");
}
/* ==========================================================================
Icon selected
========================================================================== */
.icon-star.fav::before {
color: #fff;
}
.icon-check.archive::before {
color: #fff;
}

View file

@ -17,7 +17,7 @@
/* ### Content ### */ /* ### Content ### */
/* Hide useless blocks */ /* Hide useless blocks */
body > header, body > .logo,
#article_toolbar, #article_toolbar,
#links, #links,
#sort, #sort,
@ -53,11 +53,8 @@
#main { #main {
width: 100%; width: 100%;
padding: 0;
margin: 0; margin: 0;
margin-left: 0; padding: 0;
padding-right: 0;
padding-bottom: 0;
} }
#article { #article {

View file

@ -0,0 +1,115 @@
/* ==========================================================================
"save a link" related styles
========================================================================== */
.popup-form {
background: rgba(0, 0, 0, 0.5);
position: absolute;
top: 0;
left: 10em;
z-index: 20;
height: 100%;
width: 100%;
margin: 0;
margin-top: -30% !important;
padding: 2em;
display: none;
border-left: 1px #eee solid;
form {
background-color: #fff;
position: absolute;
top: 0;
left: 0;
z-index: 20;
border: 10px solid #000;
width: 400px;
height: 200px;
padding: 2em;
}
}
#bagit-form-form .addurl {
margin-left: 0;
}
.closeMessage,
.close-button {
background-color: #000;
color: #fff;
font-size: 1.2em;
line-height: 1.6;
width: 1.6em;
height: 1.6em;
text-align: center;
text-decoration: none;
&:hover,
&:focus {
background-color: #999;
color: #000;
}
}
.close-button--popup {
display: inline-block;
position: absolute;
top: 0;
right: 0;
font-size: 1.4em;
}
.active-current {
background-color: #999;
&::after {
content: "";
width: 0;
height: 0;
position: absolute;
border: 10px solid transparent;
border-right-color: #eee;
right: 0;
top: 50%;
margin-top: -10px;
}
}
.opacity03 {
opacity: 0.3;
}
.add-to-wallabag-link-after {
background-color: #000;
color: #fff;
padding: 0 3px 2px;
}
a.add-to-wallabag-link-after {
visibility: hidden;
position: absolute;
opacity: 0;
transition-duration: 2s;
transition-timing-function: ease-out;
}
#article article a:hover + a.add-to-wallabag-link-after,
a.add-to-wallabag-link-after:hover {
opacity: 1;
visibility: visible;
transition-duration: 0.3s;
transition-timing-function: ease-in;
}
a.add-to-wallabag-link-after::after {
content: "w";
}
#add-link-result {
font-weight: bold;
font-size: 0.9em;
}
.btn-clickable {
cursor: pointer;
}

File diff suppressed because one or more lines are too long

Before

Width:  |  Height:  |  Size: 307 KiB

View file

@ -1,31 +1,19 @@
/* jQuery */
import $ from 'jquery'; import $ from 'jquery';
/* eslint-disable no-unused-vars */ /* Global imports */
/* jquery has default scope */ import '../_global/index';
import cookie from 'jquery.cookie';
import ui from 'jquery-ui-browserify';
/* eslint-enable no-unused-vars */
/* Annotations */
import annotator from 'annotator';
/* Shortcuts */ /* Shortcuts */
import './shortcuts/main'; import './js/shortcuts/main';
import './shortcuts/entry'; import './js/shortcuts/entry';
import '../../_global/js/shortcuts/main';
import '../../_global/js/shortcuts/entry';
/* Tools */ /* Tools */
import { savePercent, retrievePercent } from '../../_global/js/tools'; import toggleSaveLinkForm from './js/uiTools';
import toggleSaveLinkForm from './uiTools';
global.jquery = $; /* Theme style */
import './css/index.scss';
$.fn.ready(() => {
const $listmode = $('#listmode');
const $listentries = $('#list-entries');
$(document).ready(() => {
/* ========================================================================== /* ==========================================================================
Menu Menu
========================================================================== */ ========================================================================== */
@ -38,45 +26,12 @@ $.fn.ready(() => {
} }
}); });
/* ==========================================================================
List mode or Table Mode
========================================================================== */
$listmode.click(() => {
if ($.cookie('listmode') === 1) {
// Cookie
$.removeCookie('listmode');
$listentries.removeClass('listmode');
$listmode.removeClass('tablemode');
$listmode.addClass('listmode');
} else {
// Cookie
$.cookie('listmode', 1, { expires: 365 });
$listentries.addClass('listmode');
$listmode.removeClass('listmode');
$listmode.addClass('tablemode');
}
});
/* ==========================================================================
Cookie listmode
========================================================================== */
if ($.cookie('listmode') === 1) {
$listentries.addClass('listmode');
$listmode.removeClass('listmode');
$listmode.addClass('tablemode');
}
/* ========================================================================== /* ==========================================================================
Add tag panel Add tag panel
========================================================================== */ ========================================================================== */
$('#nav-btn-add-tag').on('click', () => { $('#nav-btn-add-tag').on('click', () => {
$('.nav-panel-add-tag').toggle(100); $('.baggy-add-tag').toggle(100);
$('.nav-panel-menu').addClass('hidden'); $('.nav-panel-menu').addClass('hidden');
$('#tag_label').focus(); $('#tag_label').focus();
return false; return false;
@ -95,39 +50,6 @@ $.fn.ready(() => {
}); });
} }
/* ==========================================================================
Annotations & Remember position
========================================================================== */
if ($('article').length) {
const app = new annotator.App();
app.include(annotator.ui.main, {
element: document.querySelector('article'),
});
const x = JSON.parse($('#annotationroutes').html());
app.include(annotator.storage.http, x);
app.start().then(() => {
app.annotations.load({ entry: x.entryId });
});
$(window).scroll(() => {
const scrollTop = $(window).scrollTop();
const docHeight = $(document).height();
const scrollPercent = (scrollTop) / (docHeight);
const scrollPercentRounded = Math.round(scrollPercent * 100) / 100;
savePercent(x.entryId, scrollPercentRounded);
});
retrievePercent(x.entryId);
$(window).resize(() => {
retrievePercent(x.entryId);
});
}
/** /**
* Close window after adding entry if popup * Close window after adding entry if popup
*/ */
@ -136,6 +58,23 @@ $.fn.ready(() => {
window.close(); window.close();
} }
/**
if ($('article').size() > 0) {
const waypoint = new Waypoint({
element: $('.wallabag-title').get(0),
handler: (direction) => {
console.log(direction);
if (direction === 'down') {
$('aside.tags').fadeIn('slow');
} else {
$('aside.tags').fadeOut('slow');
}
},
offset: 250,
});
}
*/
/** /**
* Tags autocomplete * Tags autocomplete
*/ */
@ -283,25 +222,24 @@ $.fn.ready(() => {
toggleBagit(); toggleBagit();
}); });
const $bagitFormForm = $('#bagit-form-form'); const bagitFormForm = $('#bagit-form-form');
/* ========================================================================== /* ==========================================================================
bag it link and close button bag it link and close button
========================================================================== */ ========================================================================== */
// send 'bag it link' form request via ajax // send 'bag it link' form request via ajax
$bagitFormForm.submit((event) => { bagitFormForm.submit((event) => {
$('body').css('cursor', 'wait'); $('body').css('cursor', 'wait');
$('#add-link-result').empty(); $('#add-link-result').empty();
$.ajax({ $.ajax({
type: $bagitFormForm.attr('method'), type: bagitFormForm.attr('method'),
url: $bagitFormForm.attr('action'), url: bagitFormForm.attr('action'),
data: $bagitFormForm.serialize(), data: bagitFormForm.serialize(),
success: function success() { success: function success() {
$('#add-link-result').html('Done!'); $('#add-link-result').html('Done!');
$('#plainurl').val(''); $('#plainurl').val('').blur('');
$('#plainurl').blur('');
$('body').css('cursor', 'auto'); $('body').css('cursor', 'auto');
}, },
error: function error() { error: function error() {
@ -319,7 +257,7 @@ $.fn.ready(() => {
$('article a[href^="http"]').after( $('article a[href^="http"]').after(
() => `<a href="${$(this).attr('href')}" class="add-to-wallabag-link-after" ` + () => `<a href="${$(this).attr('href')}" class="add-to-wallabag-link-after" ` +
'alt="add to wallabag" title="add to wallabag"></a>' 'title="add to wallabag"></a>',
); );
$('.add-to-wallabag-link-after').click((event) => { $('.add-to-wallabag-link-after').click((event) => {

View file

@ -1,3 +1,6 @@
import $ from 'jquery';
import Mousetrap from 'mousetrap';
$(document).ready(() => { $(document).ready(() => {
Mousetrap.bind('s', () => { Mousetrap.bind('s', () => {
$('#search').trigger('click'); $('#search').trigger('click');

View file

@ -0,0 +1,189 @@
/* ==========================================================================
Article
========================================================================== */
#article {
font-size: 20px;
margin: 0 auto;
max-width: 45em;
article {
color: #424242;
font-size: 18px;
line-height: 1.7em;
h1,
h2,
h3,
h4,
h5,
h6 {
color: #212121;
strong {
font-weight: 500;
}
}
h6 {
font-size: 1.2rem;
}
h5 {
font-size: 1.6rem;
}
h4 {
font-size: 1.9rem;
}
h3 {
font-size: 2.2rem;
}
h2 {
font-size: 2.5rem;
}
h1 {
font-size: 2.7rem;
}
a {
border-bottom: 1px dotted #03a9f4;
text-decoration: none;
}
a:hover {
border-bottom-style: solid;
}
ul {
padding-left: 30px;
}
ul,
ul li {
list-style-type: disc;
}
blockquote {
font-style: italic;
}
strong {
font-weight: bold;
}
}
img,
figure {
max-width: 100%;
height: auto;
}
pre {
box-sizing: border-box;
margin: 0 0 1.75em;
border: #e3f2fd 1px solid;
width: 100%;
padding: 10px;
font-family: monospace;
font-size: 0.8em;
white-space: pre;
overflow: auto;
background: #f5f5f5;
border-radius: 3px;
}
> header > h1 {
font-size: 2em;
margin: 2.1rem 0 0.68rem;
}
aside {
.tools {
display: flex;
flex-flow: row wrap;
.stats {
font-size: 0.8em;
margin: 8px 15px 5px;
li {
display: inline-flex;
vertical-align: middle;
margin: 0 5px;
}
a {
color: #000;
text-decoration: none;
}
}
.tags {
float: right;
margin: 5px 15px 10px;
}
}
.chip {
background-color: $blueAccentColor;
padding: 0 15px 0 10px;
margin: auto 2px;
a,
i {
color: #fff;
}
i.material-icons {
float: right;
font-size: 20px;
line-height: 32px;
padding-left: 8px;
}
}
}
}
.reader-mode {
width: 70px !important;
transition: width 0.2s ease;
.collapsible-body {
height: 0;
overflow: hidden;
}
span {
opacity: 0;
transition: opacity 0.2s ease;
}
&:hover {
width: 260px !important;
.collapsible-body {
height: auto;
li a i.material-icons {
margin: auto 5px auto -8px;
}
}
span {
opacity: 1;
}
}
}
.progress {
position: fixed;
top: 0;
width: 100%;
height: 3px;
margin: 0;
z-index: 9999;
}

View file

@ -0,0 +1,194 @@
/* ==========================================================================
Cards
========================================================================== */
main {
#content {
padding: 0 0.5rem;
}
ul.row {
padding: 0 0.75rem;
}
}
.data .card .card-body {
height: 19em;
overflow: hidden;
}
.card {
.card-content .card-title,
.card-reveal .card-title {
line-height: 22.8px;
max-height: 80px;
font-size: 19px;
font-family: roberto, "Helvetica Neue", Helvetica, Arial, sans-serif;
color: #313131;
}
.card-stacked .card-content .card-title {
display: inline-block;
}
.card-content .activator,
.card-reveal .activator {
cursor: pointer;
font-family: "Material Icons";
}
.card-content i.right,
.card-reveal i.right {
margin-left: 0;
}
.card-content .original {
line-height: 24px;
font-size: 15px;
}
.card-entry-labels {
position: absolute;
top: 10px;
z-index: 90;
max-width: 50%;
}
.card-entry-labels-hidden {
margin: 2.5px auto;
}
.card-entry-labels-hidden li {
display: inline-block;
background-color: $blueAccentColor;
margin: 0 5px;
padding: 5px 12px;
border-radius: 3px;
color: #fff;
max-height: 2em;
max-width: calc(100% - 15px);
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
.card-entry-labels-hidden li {
display: inline-block;
background-color: $blueAccentColor;
margin: 0 5px;
padding: 5px 12px;
border-radius: 3px;
color: #fff;
max-height: 2em;
max-width: calc(100% - 15px);
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
.card-content .estimatedTime {
margin-bottom: 10px;
}
.card-action {
padding: 10px 5px 10px 15px;
ul.links {
margin: 0;
font-size: 24px;
line-height: 24px;
}
a {
color: #fff;
margin: 0;
}
a:hover {
color: #fff;
}
ul.tools li a.tool {
margin-right: 5px !important;
}
.reading-time {
display: inline-flex;
vertical-align: middle;
span {
margin-right: 5px;
}
}
}
.card-image {
height: 10em;
}
.card-fullimage {
height: 13.5em;
}
.card-image .preview,
.card-fullimage .preview {
height: 14em;
background: no-repeat 50%/cover;
}
&.sw {
max-width: 370px;
margin-left: auto;
margin-right: auto;
}
}
a.original:not(.waves-effect) {
text-overflow: ellipsis;
white-space: nowrap;
overflow: hidden;
display: block;
}
.card-entry-labels li,
.card-tag-labels li {
margin: 10px 10px 10px auto;
padding: 5px 12px 5px 16px !important;
background-color: $blueAccentColor;
border-radius: 0 3px 3px 0;
color: #fff;
cursor: default;
max-height: 2em;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
}
.card-entry-tags a,
.card-entry-labels a,
.card-tag-labels a,
.card-entry-labels-hidden a,
#list .chip a {
text-decoration: none;
font-weight: normal;
color: #fff;
}
.card-stacked {
&:hover ul.tools-list {
display: block;
}
ul.tools-list {
display: none;
}
}
.quickstart .card .card-action a,
.quickstart .card .card-action a:hover {
color: #fff !important;
}
.settings .div_tabs {
padding-bottom: 15px;
}

View file

@ -0,0 +1,87 @@
/* ==========================================================================
* Entries
* ========================================================================== */
.results {
height: 1em;
.nb-results,
.pagination {
margin: 15px 15px 0;
}
.nb-results {
display: inline-flex;
}
a {
color: #444;
}
}
.pagination {
float: right;
ul {
margin: 0 !important;
.prev.disabled,
.next.disabled {
display: none;
}
}
li {
padding: 0;
}
a {
padding: 0 10px;
height: 30px;
display: block;
}
.disabled {
margin-right: 10px;
margin-left: 10px;
}
li.active span {
padding: 0 10px;
height: 30px;
display: block;
color: #fff;
}
}
.page-footer .footer-copyright {
min-width: 50px;
height: auto !important;
line-height: 1em !important;
p {
text-overflow: ellipsis;
white-space: nowrap;
overflow: hidden;
display: block;
}
}
.hidden {
display: none;
}
.picker__date-display {
display: none;
}
footer {
&.page-footer {
margin-top: 10px;
padding-top: 0;
}
.row {
margin-bottom: 10px;
}
}

View file

@ -0,0 +1,15 @@
/* ==========================================================================
* Filters slider
* ========================================================================== */
#filters {
button {
padding: 0;
width: 100%;
}
div.with-checkbox {
height: 3rem;
margin-top: 0;
}
}

View file

@ -0,0 +1,13 @@
/* ==========================================================================
* Fonts
* ========================================================================== */
/**
* Icomoon
*/
@font-face {
font-family: icomoon;
src: url("~icomoon-free-npm/Font/IcoMoon-Free.ttf");
font-weight: normal;
font-style: normal;
}

View file

@ -0,0 +1,189 @@
/* ==========================================================================
* Icons
* ========================================================================== */
/**
*
* Material icons
*
*/
.material-icons {
font-family: 'Material Icons';
font-weight: normal;
font-style: normal;
font-size: 24px; /* Preferred icon size */
width: 1em;
height: 1em;
display: inline-block;
line-height: 1;
text-transform: none;
letter-spacing: normal;
word-wrap: normal;
white-space: nowrap;
direction: ltr;
/* Support for all WebKit browsers. */
-webkit-font-smoothing: antialiased;
/* Support for Safari and Chrome. */
text-rendering: optimizeLegibility;
/* Support for Firefox. */
-moz-osx-font-smoothing: grayscale;
/* Support for IE. */
font-feature-settings: 'liga';
.md-18 {
font-size: 18px;
}
.md-24 {
font-size: 24px;
}
.md-36 {
font-size: 36px;
}
.md-48 {
font-size: 48px;
}
.md-dark {
color: rgba(0, 0, 0, 0.54);
.md-inactive {
color: rgba(0, 0, 0, 0.26);
}
}
.md-light {
color: rgba(255, 255, 255, 1);
.md-inactive {
color: rgba(255, 255, 255, 0.3);
}
}
}
/**
*
* Icomoon icons
*
*/
[class^="icon-"]::before,
[class*=" icon-"]::before {
font-family: icomoon;
speak: none;
font-style: normal;
font-weight: normal;
font-variant: normal;
text-transform: none;
line-height: 1;
background-size: 24px;
/* Enable Ligatures ================ */
letter-spacing: 0;
font-feature-settings: "liga";
}
.icon-eye::before {
content: "\e9ce";
}
.icon-no-eye::before {
content: "\e9d1";
}
.icon-calendar::before {
content: "\e953";
}
.icon-mail::before {
content: "\ea86";
}
.icon-time::before {
content: "\e952";
}
a.icon-image {
background-repeat: no-repeat;
padding-right: 0.4em !important;
padding-left: 0 !important;
margin-left: 25px;
&::before {
content: "";
display: block;
width: 24px;
height: 24px;
float: left;
margin: 7px 1.5px 0 0;
}
&.carrot::before {
background: url("../../_global/img/icons/carrot-icon--black.png") no-repeat center/90%;
}
&.diaspora::before {
background: url("../../_global/img/icons/diaspora-icon--black.png") no-repeat center/80%;
}
&.unmark::before {
background: url("../../_global/img/icons/unmark-icon--black.png") no-repeat center/80%;
}
&.shaarli::before {
background: url("../../_global/img/icons/shaarli.png") no-repeat center/80%;
}
&.scuttle::before {
background: url("../../_global/img/icons/scuttle.png") no-repeat center/80%;
}
}
.icon-google-plus2::before {
content: "\ea89";
}
.icon-facebook2::before {
content: "\ea8d";
}
.icon-twitter::before {
content: "\ea96";
}
.icon-apple::before {
content: "\eabf";
}
.icon-android::before {
content: "\eac1";
}
.icon-chrome::before {
content: "\eae5";
}
.icon-firefox::before {
content: "\eae6";
}
.icon-link::before {
content: "\e9cb";
}
footer [class^="icon-"],
footer [class*=" icon-"] {
font-size: 2em;
transition: text-shadow 0.2s ease;
padding-right: 10px;
}
footer [class^="icon-"]:hover,
footer [class*=" icon-"]:hover {
text-shadow: 0 0 10px rgba(0, 0, 0, 0.3);
}

View file

@ -0,0 +1,17 @@
@import 'variables';
/* Style */
@import 'article';
@import 'cards';
@import 'entries';
@import 'filters';
@import 'layout';
@import 'nav';
@import 'sidenav';
@import 'various';
/* Tools */
@import 'fonts';
@import 'icons';
@import 'print';
@import 'media_queries';

View file

@ -0,0 +1,50 @@
/* ==========================================================================
Layout
========================================================================== */
body {
display: flex;
min-height: 100vh;
flex-direction: column;
background: #fafafa;
&.login main {
padding: 0;
min-height: 100vh;
}
}
.border-bottom {
border-bottom: 1px solid #ddd;
}
nav,
main,
footer {
padding-left: 240px;
}
main,
#content,
.valign-wrapper {
height: 100%;
}
#main {
flex: 1 0 auto;
.logo {
a {
height: 100pt;
}
img {
height: 100pt;
width: 100pt;
}
&:hover {
background: transparent;
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -0,0 +1,149 @@
/* ==========================================================================
Media queries
========================================================================== */
@media only screen and (max-width: 992px) {
header,
main,
footer {
padding-left: 0;
}
nav,
main,
footer {
padding-left: 0;
}
.pagination {
width: auto;
}
.nav-panels .action {
padding-right: 0.75rem;
}
.nav-panel-buttom {
justify-content: space-around;
}
#article {
max-width: 35em;
margin-left: auto;
margin-right: auto;
font-size: 18px;
> header > h1 {
font-size: 1.33em;
}
}
.reader-mode {
width: 240px !important;
span {
opacity: 1;
}
}
.tabs {
display: inline-block;
height: auto;
}
.tab {
min-width: 100%;
}
.indicator {
display: none;
}
.pagination li.prev,
.pagination li.next {
width: auto;
}
.drag-target + .drag-target {
height: 50%;
}
.drag-target + .drag-target + .drag-target {
top: 50%;
}
}
@media only screen and (min-width: 1200px) and (max-width: 1650px) {
.row .col.l3 {
width: 33.33333%;
margin-left: 0;
}
}
@media only screen and (min-width: 993px) and (max-width: 1200px) {
.row {
.col.l1 {
width: 25%;
margin-left: 0;
}
.col.l2 {
width: 33.33333%;
margin-left: 0;
}
.col.l3 {
width: 41.66667%;
margin-left: 0;
}
.col.l4 {
width: 50%;
margin-left: 0;
}
.col.l5 {
width: 58.33333%;
margin-left: 0;
}
.col.l6 {
width: 66.66667%;
margin-left: 0;
}
.col.l7 {
width: 75%;
margin-left: 0;
}
.col.l8 {
width: 83.33333%;
margin-left: 0;
}
.col.l9 {
width: 91.66667%;
margin-left: 0;
}
.col.l10 {
width: 100%;
margin-left: 0;
}
}
}
@media only screen and (max-width: 350px) {
.nb-results {
display: none;
}
main ul.row {
padding: 0;
}
.row .col {
padding: 0;
}
}

View file

@ -0,0 +1,106 @@
/* ==========================================================================
Nav
========================================================================== */
nav {
height: auto;
input {
color: #aaa;
}
ul a:hover {
background-color: initial;
}
}
.nav-wrapper {
display: flex;
flex-wrap: wrap;
justify-content: space-between;
min-height: 64px;
.button-collapse {
padding: 0 15px;
}
}
.nav-input {
display: none;
}
.nav-panel-buttom {
display: flex;
flex-grow: 1;
justify-content: flex-end;
li {
max-height: 64px;
}
}
.nav-panel-add .add,
.nav-panel-search .search,
.nav-panels .close {
color: #444 !important;
}
.nav-panels {
transition: background 0.2s ease;
.action {
padding-left: 0.75rem;
font-size: 2.1rem;
white-space: nowrap;
}
.input-field input {
display: block;
line-height: inherit;
padding-left: 4rem !important;
width: calc(100% - 8rem);
height: 4.1rem;
}
.input-field input:focus {
background-color: #fff;
border: 0;
box-shadow: none;
color: #444;
}
}
.input-field {
&.nav-panel-add label,
&.nav-panel-search label {
left: 1rem;
}
&.nav-panel-add .close,
&.nav-panel-search .close {
position: absolute;
top: 0;
right: 1rem;
color: transparent;
cursor: pointer;
font-size: 2rem;
transition: 0.3s color;
}
&.nav-panel-add,
&.nav-panel-add form,
&.nav-panel-search,
&.nav-panel-search form {
display: flex;
flex: 1;
}
}
#button_filters {
display: none;
}
#button_export {
display: none;
}

View file

@ -64,11 +64,8 @@
#main { #main {
width: 100%; width: 100%;
padding: 0;
margin: 0; margin: 0;
margin-left: 0; padding: 0;
padding-right: 0;
padding-bottom: 0;
} }
#article { #article {

View file

@ -0,0 +1,45 @@
/* ==========================================================================
Side-nav
========================================================================== */
.side-nav {
width: 240px;
li {
padding: 0;
&.logo > a:hover {
background: initial;
}
}
a {
margin: 0;
}
&.fixed a {
font-size: 13px;
line-height: 44px;
height: 44px;
}
.collapsible-header,
&.fixed .collapsible-header {
height: 45px;
line-height: 44px;
padding: 0 20px;
}
> li.logo {
line-height: 0;
text-align: center;
}
}
.bold > a {
font-weight: bold;
}
span.numberItems {
float: right;
}

View file

@ -0,0 +1,5 @@
/* ==========================================================================
Variables
========================================================================== */
$blueAccentColor: rgba(0, 151, 167, 0.85);

View file

@ -0,0 +1,32 @@
/* ==========================================================================
* Various
* ========================================================================== */
div.settings div.file-field {
/* force height on non-input field in the settings page */
div,
ul {
margin-top: 40px;
}
/* but avoid to kill all file input */
div {
margin-top: inherit;
}
}
.input-field label.active {
font-size: 1rem;
}
nav .input-field input {
margin: 0;
}
.tabs {
display: flex;
}
.tab {
flex: 1;
}

View file

@ -1,21 +1,21 @@
/* jQuery */
import $ from 'jquery'; import $ from 'jquery';
/* Annotations */ /* Materialize imports */
import annotator from 'annotator'; import 'materialize-css/dist/css/materialize.css';
import 'materialize-css/dist/js/materialize';
/* Global imports */
import '../_global/index';
/* Tools */ /* Tools */
import { savePercent, retrievePercent, initFilters, initExport } from '../../_global/js/tools'; import { initExport, initFilters } from './js/tools';
/* Import shortcuts */ /* Import shortcuts */
import './shortcuts/main'; import './js/shortcuts/main';
import './shortcuts/entry'; import './js/shortcuts/entry';
import '../../_global/js/shortcuts/main';
import '../../_global/js/shortcuts/entry';
require('materialize'); // eslint-disable-line /* Theme style */
import './css/index.scss';
global.jQuery = $;
$(document).ready(() => { $(document).ready(() => {
// sideNav // sideNav
@ -30,6 +30,7 @@ $(document).ready(() => {
formatSubmit: 'dd/mm/yyyy', formatSubmit: 'dd/mm/yyyy',
hiddenName: true, hiddenName: true,
format: 'dd/mm/yyyy', format: 'dd/mm/yyyy',
container: 'body',
}); });
initFilters(); initFilters();
initExport(); initExport();
@ -74,37 +75,4 @@ $(document).ready(() => {
const scrollPercent = (s / (d - c)) * 100; const scrollPercent = (s / (d - c)) * 100;
$('.progress .determinate').css('width', `${scrollPercent}%`); $('.progress .determinate').css('width', `${scrollPercent}%`);
}); });
/* ==========================================================================
Annotations & Remember position
========================================================================== */
if ($('article').length) {
const app = new annotator.App();
const x = JSON.parse($('#annotationroutes').html());
app.include(annotator.ui.main, {
element: document.querySelector('article'),
});
app.include(annotator.storage.http, x);
app.start().then(() => {
app.annotations.load({ entry: x.entryId });
});
$(window).scroll(() => {
const scrollTop = $(window).scrollTop();
const docHeight = $(document).height();
const scrollPercent = (scrollTop) / (docHeight);
const scrollPercentRounded = Math.round(scrollPercent * 100) / 100;
savePercent(x.entryId, scrollPercentRounded);
});
retrievePercent(x.entryId);
$(window).resize(() => {
retrievePercent(x.entryId);
});
}
}); });

View file

@ -28,6 +28,11 @@ $(document).ready(() => {
return; return;
} }
/* Show nothing on login/register page */
if ($('#username').length > 0 || $('#fos_user_registration_form_username').length > 0) {
return;
}
/* Focus current card */ /* Focus current card */
toggleFocus(card); toggleFocus(card);

View file

@ -0,0 +1,24 @@
import $ from 'jquery';
function initFilters() {
// no display if filters not available
if ($('div').is('#filters')) {
$('#button_filters').show();
$('.js-filters-action').sideNav({ edge: 'right' });
$('#clear_form_filters').on('click', () => {
$('#filters input').val('');
$('#filters :checked').removeAttr('checked');
return false;
});
}
}
function initExport() {
// no display if export not available
if ($('div').is('#export')) {
$('#button_export').show();
$('.js-export-action').sideNav({ edge: 'right' });
}
}
export { initExport, initFilters };

View file

@ -3,6 +3,10 @@ imports:
- { resource: security.yml } - { resource: security.yml }
- { resource: services.yml } - { resource: services.yml }
parameters:
# Allows to use the live reload feature for changes in assets
use_webpack_dev_server: false
framework: framework:
#esi: ~ #esi: ~
translator: translator:

View file

@ -1,9 +1,9 @@
imports: imports:
- { resource: config.yml } - { resource: config.yml }
#framework: framework:
# cache: assets:
# system: cache.adapter.apcu # json_manifest_path: '%kernel.root_dir%/../web/bundles/wallabagcore/manifest.json'
#doctrine: #doctrine:
# orm: # orm:

View file

@ -0,0 +1,40 @@
const path = require('path');
const webpack = require('webpack');
const StyleLintPlugin = require('stylelint-webpack-plugin');
const rootDir = path.resolve(__dirname, '../../../');
module.exports = function() {
return {
entry: {
material: path.join(rootDir, './app/Resources/static/themes/material/index.js'),
baggy: path.join(rootDir, './app/Resources/static/themes/baggy/index.js'),
},
output: {
filename: '[name].js',
path: path.resolve(rootDir, 'web/bundles/wallabagcore'),
publicPath: '/bundles/wallabagcore/',
},
plugins: [
new webpack.ProvidePlugin({
$: 'jquery',
jQuery: 'jquery',
'window.$': 'jquery',
'window.jQuery': 'jquery'
}),
new StyleLintPlugin({
configFile: '.stylelintrc',
failOnError: false,
quiet: false,
context: 'app/Resources/static/themes',
files: '**/*.scss',
}),
],
resolve: {
alias: {
jquery: path.join(rootDir, 'node_modules/jquery/dist/jquery.js')
}
},
};
};

62
app/config/webpack/dev.js Normal file
View file

@ -0,0 +1,62 @@
const webpackMerge = require('webpack-merge');
const webpack = require('webpack');
const path = require('path');
const commonConfig = require('./common.js');
module.exports = function () {
return webpackMerge(commonConfig(), {
devtool: 'eval-source-map',
output: {
filename: '[name].dev.js'
},
devServer: {
hot: true,
// enable HMR on the server
contentBase: './web',
// match the output path
},
plugins: [
new webpack.HotModuleReplacementPlugin(),
],
module: {
rules: [
{
enforce: 'pre',
test: /\.js$/,
loader: 'eslint-loader',
exclude: /node_modules/,
},
{
test: /\.js$/,
exclude: /(node_modules)/,
use: {
loader: 'babel-loader',
options: {
presets: ['env']
}
}
},
{
test: /\.(s)?css$/,
use: [
'style-loader',
{
loader: 'css-loader',
options: {
importLoaders: 1,
}
},
'postcss-loader',
'sass-loader'
]
},
{
test: /\.(jpg|png|gif|svg|eot|ttf|woff|woff2)$/,
use: 'url-loader'
},
]
},
})
};

View file

@ -0,0 +1,99 @@
const webpack = require('webpack');
const webpackMerge = require('webpack-merge');
const ExtractTextPlugin = require('extract-text-webpack-plugin');
const ManifestPlugin = require('webpack-manifest-plugin');
const commonConfig = require('./common.js');
module.exports = function() {
return webpackMerge(commonConfig(), {
output: {
filename: '[name].js'
},
devtool: 'source-map',
plugins: [
new webpack.DefinePlugin({
'process.env': {
'NODE_ENV': JSON.stringify('production')
}
}),
new webpack.optimize.UglifyJsPlugin({
beautify: false,
mangle: {
screw_ie8: true,
keep_fnames: true
},
compress: {
screw_ie8: true,
warnings: false
},
comments: false
}),
new ExtractTextPlugin('[name].css'),
new ManifestPlugin({
fileName: 'manifest.json',
})
],
module: {
rules: [
{
enforce: 'pre',
test: /\.js$/,
loader: 'eslint-loader',
exclude: /node_modules/,
},
{
test: /\.js$/,
exclude: /(node_modules)/,
use: {
loader: 'babel-loader',
options: {
presets: ['env']
}
}
},
{
test: /\.(s)?css$/,
use: ExtractTextPlugin.extract({
fallback: 'style-loader',
use: [
{
loader: 'css-loader',
options: {
importLoaders: 1,
minimize: {
discardComments: {
removeAll: true
},
core: true,
minifyFontValues: true
}
}
},
'postcss-loader',
'sass-loader'
]
})
},
{
test: /\.(jpg|png|gif|svg)$/,
use: {
loader: 'file-loader',
options: {
name: 'img/[name].[ext]',
}
}
},
{
test: /\.(eot|ttf|woff|woff2)$/,
use: {
loader: 'file-loader',
options: {
name: 'fonts/[name].[ext]',
}
}
}
]
},
})
};

View file

@ -0,0 +1,33 @@
Tips for front-end developers
=============================
Starting from version 2.3, wallabag uses webpack to bundle its assets.
Dev mode
--------
If the server runs in dev mode, you need to run ``yarn run build:dev`` to generate the outputted javascript files for each theme. These are named ``%theme%.dev.js`` and are ignored by git. You need to relaunch ``yarn run build:dev`` for each change made to one of the assets files (js, css, pictures, fonts,...).
Live reload
-----------
Webpack brings support for live reload, which means you don't need to regenerate the assets file for each change neither reload the page manually. Changes are applied automatically in the web page. Just set the ``use_webpack_dev_server`` setting to ``true`` in ``app/config/config.yml`` and run ``yarn run watch`` and you're good to go.
.. note::
Don't forget to put back ``use_webpack_dev_server`` to ``false`` when not using the live reload feature.
Production builds
-----------------
When you want to commit your changes, build them in production environment by using ``yarn run build:prod``. This will build all the assets needed for wallabag. To test that it properly works, you'll need to have a server in production mode, for instance with ``bin/console server:run -e=prod``.
.. note::
Don't forget to generate production builds before committing !
Code style
----------
Code style is checked by two tools : stylelint for (S)CSS and eslint for JS. ESlint config is based on the Airbnb base preset.

View file

@ -0,0 +1,33 @@
Conseils pour développeurs front-end
====================================
Depuis la version 2.3, wallabag utilise webpack pour générer ses assets.
Mode développeur
----------------
Si le serveur fonctionne en mode dev, vous devez lancer la commande ``yarn run build:dev`` pour générer les fichiers de sortie javascript pour chaque thème. Ils sont nommés ``%theme%.dev.js`` et sont ignorés par git. Vous devez relancer la commande ``yarn run build:dev`` pour chaque changement que vous effectuez dans les fichiers assets (js, css, images, polices,...).
Live reload
-----------
Webpack apporte le support pour la fonctionnalité de live reload, ce qui signifie que vous n'avez pas besoin de regénérer manuellement le fichier de sortie javascript ni de rafraichir la page dans votre navigateur. Les changements sont appliqués automatiquement. Vous avez juste besoin de mettre le paramètre ``use_webpack_dev_server`` à ``true`` dans ``app/config/config.yml`` et de lancer ``yarn run watch`` pour que cela soit actif.
.. note::
N'oubliez pas de remettre ``use_webpack_dev_server`` à ``false`` lorsque vous n'utilisez pas la fonctionnalité de live reload.
Production builds
-----------------
Lorsque vous committez vos changements, vous devez les compiler dans un environnement de production en exécutant ``yarn run build:prod``. Cela compilera tous les assets nécessaires pour wallabag. Pour tester que cela fonctionne proprement, vous devrez avoir un serveur en mode de production, par exemple avec ``bin/console server:run -e=prod``.
.. note::
N'oubliez pas de générer des fichiers en mode production avant de committer !
Code style
----------
Le style de code est vérifié par deux outils : stylelint pour le (S)CSS et eslint pour le JS. La configuration ESlint config est basée sur le preset Airbnb base.

View file

@ -1,34 +1,13 @@
{ {
"name": "wallabag", "name": "wallabag",
"version": "2.1.0", "version": "2.2.2",
"description": "wallabag is a self hostable application for saving web pages", "description": "wallabag is a self hostable application for saving web pages",
"main": "index.js",
"private": true, "private": true,
"directories": { "directories": {
"doc": "docs" "doc": "docs"
}, },
"engines": { "engines": {
"node": ">0.12" "node": ">4.8"
},
"browser": {
"jquery": "./node_modules/jquery/dist/jquery.js",
"jQuery": "./node_modules/jquery/dist/jquery.js",
"materialize": "./node_modules/materialize-css/bin/materialize.js"
},
"browserify-shim": {
"jquery": {
"exports": "$"
},
"materialize": "materialize",
"jquery-ui": {
"depends": "jquery",
"exports": null
}
},
"browserify": {
"transform": [
"browserify-shim"
]
}, },
"repository": { "repository": {
"type": "git", "type": "git",
@ -57,52 +36,49 @@
"url": "https://github.com/wallabag/wallabag/issues" "url": "https://github.com/wallabag/wallabag/issues"
}, },
"devDependencies": { "devDependencies": {
"annotator": "git://github.com/wallabag/annotator.git#0f076c7d371ed25eb0793346f46982d90f2c4c85", "autoprefixer": "^6.7.7",
"autoprefixer": "^6.3.6", "babel-core": "^6.24.1",
"babel-eslint": "^6.1.2", "babel-eslint": "^7.2.3",
"babel-preset-es2015": "^6.14.0", "babel-loader": "^7.0.0",
"babelify": "^7.3.0", "babel-preset-env": "^1.4.0",
"browserify": "^13.0.0", "css-loader": "^0.28.0",
"browserify-shim": "^3.8.12", "eslint": "^3.19.0",
"cssnano": "^3.5.2", "eslint-config-airbnb-base": "^11.1.3",
"es6-promise": "^3.2.1", "eslint-loader": "^1.7.1",
"eslint": "^3.7.1", "eslint-plugin-import": "^2.2.0",
"eslint-config-airbnb-base": "^8.0.0", "extract-text-webpack-plugin": "^2.1.0",
"eslint-plugin-import": "^1.16.0", "file-loader": "^0.11.0",
"grunt": ">=0.4.0", "lato-font": "^3.0.0",
"grunt-browserify": "^5.0.0", "node-sass": "^4.5.2",
"grunt-cli": "^1.2.0", "postcss-loader": "^1.3.3",
"grunt-contrib-clean": "^1.0.0", "sass-loader": "^6.0.3",
"grunt-contrib-concat": "^1.0.0", "style-loader": "^0.16.1",
"grunt-contrib-copy": "^1.0.0", "stylelint": "^7.9.0",
"grunt-contrib-symlink": "^1.0.0", "stylelint-config-standard": "^16.0.0",
"grunt-contrib-uglify": "^1.0.0", "stylelint-webpack-plugin": "^0.7.0",
"grunt-contrib-watch": "^1.0.0", "url-loader": "^0.5.8",
"grunt-eslint": "^19.0.0", "webpack": "^2.3.2",
"grunt-postcss": "^0.8.0", "webpack-dev-server": "^2.4.4",
"grunt-stylelint": "^0.6.0", "webpack-manifest-plugin": "^1.1.0",
"hammerjs": "^2.0.6", "webpack-merge": "^4.1.0"
"icomoon-free-npm": "0.0.0",
"jquery": "^2.2.4",
"jquery-ui-browserify": "^1.11.0-pre-seelio",
"jquery.cookie": "^1.4.1",
"jquery.tinydot": "^0.2.1",
"load-grunt-tasks": "^3.4.1",
"material-design-icons-iconfont": "^3.0.0",
"materialize-css": "0.97.5",
"npm": "^3.8.3",
"pickadate": "^3.5.6",
"pixrem": "^3.0.0",
"postcss-cssnext": "^2.5.1",
"prismjs": "^1.4.1",
"ptsans-npm-webfont": "0.0.4",
"roboto-fontface": "^0.6.0",
"stylelint": "^7.3.1",
"stylelint-config-standard": "^13.0.2",
"through": "^2.3.8"
}, },
"dependencies": { "dependencies": {
"jr-qrcode": "^1.0.5", "annotator": "git://github.com/wallabag/annotator.git#0f076c7d371ed25eb0793346f46982d90f2c4c85",
"mousetrap": "^1.6.0" "hammerjs": "^2.0.8",
"icomoon-free-npm": "^0.0.0",
"jquery": "^2.1.4",
"jquery.cookie": "^1.4.1",
"jr-qrcode": "^1.0.7",
"material-design-icons-iconfont": "^3.0.3",
"materialize-css": "^0.98.1",
"mousetrap": "^1.6.0",
"ptsans-npm-webfont": "^0.0.4",
"roboto-fontface": "^0.7.0",
"waypoints": "^4.0.1"
},
"scripts": {
"watch": "./node_modules/.bin/webpack-dev-server --env=dev",
"build:dev": "./node_modules/.bin/webpack --env=dev",
"build:prod": "./node_modules/.bin/webpack --env=prod"
} }
} }

7
postcss.config.js Normal file
View file

@ -0,0 +1,7 @@
module.exports = {
plugins: function () {
return [
require('autoprefixer'),
];
}
};

View file

@ -17,9 +17,9 @@
<div class="results"> <div class="results">
<div class="nb-results">{{ 'entry.list.number_on_the_page'|transchoice(entries.count) }}</div> <div class="nb-results">{{ 'entry.list.number_on_the_page'|transchoice(entries.count) }}</div>
<div class="pagination"> <div class="pagination">
<a href="{{ path('switch_view_mode') }}"><i class="listMode-btn material-icons md-36">{% if listMode == 0 %}list{% else %}view_module{% endif %}</i></a> <a href="{{ path('switch_view_mode') }}"><i class="listMode-btn material-icons md-24">{% if listMode == 0 %}list{% else %}view_module{% endif %}</i></a>
<i class="btn-clickable download-btn material-icons md-36 js-export-action">file_download</i> <i class="btn-clickable download-btn material-icons md-24 js-export-action">file_download</i>
<i class="btn-clickable filter-btn material-icons md-36 js-filters-action">filter_list</i> <i class="btn-clickable filter-btn material-icons md-24 js-filters-action">filter_list</i>
{% if entries.getNbPages > 1 %} {% if entries.getNbPages > 1 %}
{{ pagerfanta(entries, 'twitter_bootstrap_translated', {'proximity': 1}) }} {{ pagerfanta(entries, 'twitter_bootstrap_translated', {'proximity': 1}) }}
{% endif %} {% endif %}
@ -47,10 +47,10 @@
</div> </div>
<ul class="tools links"> <ul class="tools links">
<li><a title="{{ 'entry.list.toogle_as_read'|trans }}" class="tool icon-check icon {% if entry.isArchived == 0 %}archive-off{% else %}archive{% endif %}" href="{{ path('archive_entry', { 'id': entry.id }) }}"><span>{{ 'entry.list.toogle_as_read'|trans }}</span></a></li> <li><a href="{{ entry.url|e }}" target="_blank" title="{{ 'entry.list.original_article'|trans }} : {{ entry.title|e }}"><span>{{ entry.domainName|removeWww }}</span></a></li>
<li><a title="{{ 'entry.list.toogle_as_star'|trans }}" class="tool icon-star icon {% if entry.isStarred == 0 %}fav-off{% else %}fav{% endif %}" href="{{ path('star_entry', { 'id': entry.id }) }}"><span>{{ 'entry.list.toogle_as_star'|trans }}</span></a></li> <li><a title="{{ 'entry.list.toogle_as_read'|trans }}" class="tool icon {% if entry.isArchived == 0 %}archive-off{% else %}archive{% endif %}" href="{{ path('archive_entry', { 'id': entry.id }) }}"><i class="material-icons md-24 vertical-align-middle">check</i><span>{{ 'entry.list.toogle_as_read'|trans }}</span></a></li>
<li><a title="{{ 'entry.list.delete'|trans }}" class="tool delete icon-trash icon" href="{{ path('delete_entry', { 'id': entry.id }) }}"><span>{{ 'entry.list.delete'|trans }}</span></a></li> <li><a title="{{ 'entry.list.toogle_as_star'|trans }}" class="tool icon {% if entry.isStarred == 0 %}fav-off{% else %}fav{% endif %}" href="{{ path('star_entry', { 'id': entry.id }) }}"><i class="material-icons md-24 vertical-align-middle">star_rate</i><span>{{ 'entry.list.toogle_as_star'|trans }}</span></a></li>
<li><a href="{{ entry.url|e }}" target="_blank" title="{{ 'entry.list.original_article'|trans }} : {{ entry.title|e }}" class="tool link icon-link icon"><span>{{ entry.domainName|removeWww }}</span></a></li> <li><a title="{{ 'entry.list.delete'|trans }}" class="tool icon" href="{{ path('delete_entry', { 'id': entry.id }) }}"><i class="material-icons md-24 vertical-align-middle">delete</i><span>{{ 'entry.list.delete'|trans }}</span></a></li>
</ul> </ul>
{% if (entry.previewPicture is null or listMode == 1) %} {% if (entry.previewPicture is null or listMode == 1) %}
<ul class="card-entry-tags"> <ul class="card-entry-tags">

View file

@ -77,7 +77,7 @@
<span class="label-outline"><i class="material-icons">label_outline</i> <a href="{{ path('tag_entries', {'slug': tag.slug}) }}">{{ tag.label }}</a> <a href="{{ path('remove_tag', { 'entry': entry.id, 'tag': tag.id }) }}" class="nostyle"><i>✘</i></a></span> <span class="label-outline"><i class="material-icons">label_outline</i> <a href="{{ path('tag_entries', {'slug': tag.slug}) }}">{{ tag.label }}</a> <a href="{{ path('remove_tag', { 'entry': entry.id, 'tag': tag.id }) }}" class="nostyle"><i>✘</i></a></span>
{% endfor %} {% endfor %}
</div> </div>
<div class="input-field nav-panel-add-tag" style="display: none"> <div class="input-field baggy-add-tag" style="display: none">
{{ render(controller( "WallabagCoreBundle:Tag:addTagForm", { 'id': entry.id } )) }} {{ render(controller( "WallabagCoreBundle:Tag:addTagForm", { 'id': entry.id } )) }}
</div> </div>
</aside> </aside>

View file

@ -2,12 +2,14 @@
{% block css %} {% block css %}
{{ parent() }} {{ parent() }}
<link rel="stylesheet" href="{{ asset('bundles/wallabagcore/themes/baggy/css/style.min.css') }}" media="screen,projection,print"/> {% if not app.debug %}
<link rel="stylesheet" href="{{ asset('bundles/wallabagcore/baggy.css') }}">
{% endif %}
{% endblock %} {% endblock %}
{% block scripts %} {% block scripts %}
{{ parent() }} {{ parent() }}
<script src="{{ asset('bundles/wallabagcore/themes/baggy/js/baggy.min.js') }}"></script> <script src="{{ asset('bundles/wallabagcore/baggy' ~ (app.debug ? '.dev' : '') ~ '.js') }}"></script>
{% endblock %} {% endblock %}
{% block header %} {% block header %}

View file

@ -25,9 +25,9 @@
<div class="row"> <div class="row">
<div class="input-field col s11"> <div class="input-field col s11">
{{ form_label(form.config.theme) }}
{{ form_errors(form.config.theme) }} {{ form_errors(form.config.theme) }}
{{ form_widget(form.config.theme) }} {{ form_widget(form.config.theme) }}
{{ form_label(form.config.theme) }}
</div> </div>
<div class="input-field col s1"> <div class="input-field col s1">
<a href="#" class="tooltipped" data-position="left" data-delay="50" data-tooltip="{{ 'config.form_settings.help_theme'|trans }}"> <a href="#" class="tooltipped" data-position="left" data-delay="50" data-tooltip="{{ 'config.form_settings.help_theme'|trans }}">
@ -38,9 +38,9 @@
<div class="row"> <div class="row">
<div class="input-field col s11"> <div class="input-field col s11">
{{ form_label(form.config.items_per_page) }}
{{ form_errors(form.config.items_per_page) }} {{ form_errors(form.config.items_per_page) }}
{{ form_widget(form.config.items_per_page) }} {{ form_widget(form.config.items_per_page) }}
{{ form_label(form.config.items_per_page) }}
</div> </div>
<div class="input-field col s1"> <div class="input-field col s1">
<a href="#" class="tooltipped" data-position="left" data-delay="50" data-tooltip="{{ 'config.form_settings.help_items_per_page'|trans }}"> <a href="#" class="tooltipped" data-position="left" data-delay="50" data-tooltip="{{ 'config.form_settings.help_items_per_page'|trans }}">
@ -51,9 +51,9 @@
<div class="row"> <div class="row">
<div class="input-field col s11"> <div class="input-field col s11">
{{ form_label(form.config.reading_speed) }}
{{ form_errors(form.config.reading_speed) }} {{ form_errors(form.config.reading_speed) }}
{{ form_widget(form.config.reading_speed) }} {{ form_widget(form.config.reading_speed) }}
{{ form_label(form.config.reading_speed) }}
<p> <p>
{{ 'config.form_settings.reading_speed.help_message'|trans }} {{ 'config.form_settings.reading_speed.help_message'|trans }}
<a href="http://www.myreadspeed.com/calculate/">myreadspeed</a> <a href="http://www.myreadspeed.com/calculate/">myreadspeed</a>
@ -68,17 +68,17 @@
<div class="row"> <div class="row">
<div class="input-field col s12"> <div class="input-field col s12">
{{ form_label(form.config.action_mark_as_read) }}
{{ form_errors(form.config.action_mark_as_read) }} {{ form_errors(form.config.action_mark_as_read) }}
{{ form_widget(form.config.action_mark_as_read) }} {{ form_widget(form.config.action_mark_as_read) }}
{{ form_label(form.config.action_mark_as_read) }}
</div> </div>
</div> </div>
<div class="row"> <div class="row">
<div class="input-field col s11"> <div class="input-field col s11">
{{ form_label(form.config.language) }}
{{ form_errors(form.config.language) }} {{ form_errors(form.config.language) }}
{{ form_widget(form.config.language) }} {{ form_widget(form.config.language) }}
{{ form_label(form.config.language) }}
</div> </div>
<div class="input-field col s1"> <div class="input-field col s1">
<a href="#" class="tooltipped" data-position="left" data-delay="50" data-tooltip="{{ 'config.form_settings.help_language'|trans }}"> <a href="#" class="tooltipped" data-position="left" data-delay="50" data-tooltip="{{ 'config.form_settings.help_language'|trans }}">
@ -89,9 +89,9 @@
<div class="row"> <div class="row">
<div class="input-field col s11"> <div class="input-field col s11">
{{ form_label(form.config.pocket_consumer_key) }}
{{ form_errors(form.config.pocket_consumer_key) }} {{ form_errors(form.config.pocket_consumer_key) }}
{{ form_widget(form.config.pocket_consumer_key) }} {{ form_widget(form.config.pocket_consumer_key) }}
{{ form_label(form.config.pocket_consumer_key) }}
<p> <p>
&raquo; &raquo;
<a href="https://getpocket.com/developer/docs/authentication">https://getpocket.com/developer/docs/authentication</a> <a href="https://getpocket.com/developer/docs/authentication">https://getpocket.com/developer/docs/authentication</a>
@ -132,8 +132,8 @@
</div> </div>
<div class="row"> <div class="row">
<div class="input-field col s12"> <div class="col s12">
<label>{{ 'config.form_rss.token_label'|trans }}</label> <h6 class="grey-text">{{ 'config.form_rss.token_label'|trans }}</h6>
<div> <div>
{% if rss.token %} {% if rss.token %}
{{ rss.token }} {{ rss.token }}
@ -151,8 +151,8 @@
</div> </div>
{% if rss.token %} {% if rss.token %}
<div class="row"> <div class="row">
<div class="input-field col s12"> <div class="col s12">
<label>{{ 'config.form_rss.rss_links'|trans }}</label> <h6 class="grey-text">{{ 'config.form_rss.rss_links'|trans }}</h6>
<ul> <ul>
<li><a href="{{ path('unread_rss', {'username': rss.username, 'token': rss.token}) }}">{{ 'config.form_rss.rss_link.unread'|trans }}</a></li> <li><a href="{{ path('unread_rss', {'username': rss.username, 'token': rss.token}) }}">{{ 'config.form_rss.rss_link.unread'|trans }}</a></li>
<li><a href="{{ path('starred_rss', {'username': rss.username, 'token': rss.token}) }}">{{ 'config.form_rss.rss_link.starred'|trans }}</a></li> <li><a href="{{ path('starred_rss', {'username': rss.username, 'token': rss.token}) }}">{{ 'config.form_rss.rss_link.starred'|trans }}</a></li>

View file

@ -1,7 +1,7 @@
{% set readingTime = entry.readingTime / app.user.config.readingSpeed %} {% set readingTime = entry.readingTime / app.user.config.readingSpeed %}
<i class="material-icons">timer</i> <i class="material-icons">timer</i>
{% if readingTime > 0 %} {% if readingTime > 0 %}
{{ 'entry.list.reading_time_minutes_short'|trans({'%readingTime%': readingTime|round}) }} <span>{{ 'entry.list.reading_time_minutes_short'|trans({'%readingTime%': readingTime|round}) }}</span>
{% else %} {% else %}
{{ 'entry.list.reading_time_less_one_minute_short'|trans|raw }} <span>{{ 'entry.list.reading_time_less_one_minute_short'|trans|raw }}</span>
{% endif %} {% endif %}

View file

@ -45,7 +45,7 @@
{% endif %} {% endif %}
<!-- Export --> <!-- Export -->
<div id="export" class="side-nav fixed right-aligned"> <div id="export" class="side-nav right-aligned">
{% set currentRoute = app.request.attributes.get('_route') %} {% set currentRoute = app.request.attributes.get('_route') %}
{% set currentTag = '' %} {% set currentTag = '' %}
{% if tag is defined %} {% if tag is defined %}
@ -68,7 +68,7 @@
<!-- Filters --> <!-- Filters -->
{% if form is not null %} {% if form is not null %}
<div id="filters" class="side-nav fixed right-aligned"> <div id="filters" class="side-nav right-aligned">
<form action="{{ path('all') }}"> <form action="{{ path('all') }}">
<h4 class="center">{{ 'entry.filters.title'|trans }}</h4> <h4 class="center">{{ 'entry.filters.title'|trans }}</h4>

View file

@ -125,47 +125,43 @@
{% endif %} {% endif %}
{% if craue_setting('share_shaarli') %} {% if craue_setting('share_shaarli') %}
<li> <li>
<a href="{{ craue_setting('shaarli_url') }}/index.php?post={{ entry.url|url_encode }}&amp;title={{ entry.title|striptags|url_encode }}&amp;tags={{ entry.tags|join(',')|striptags|url_encode }}" target="_blank"> <a href="{{ craue_setting('shaarli_url') }}/index.php?post={{ entry.url|url_encode }}&amp;title={{ entry.title|striptags|url_encode }}&amp;tags={{ entry.tags|join(',')|striptags|url_encode }}" target="_blank" title="shaarli" class="tool icon-image shaarli">
<i class="tool icon-image icon-image--shaarli" title="shaarli"></i>
<span>shaarli</span> <span>shaarli</span>
</a> </a>
</li> </li>
{% endif %} {% endif %}
{% if craue_setting('share_scuttle') %} {% if craue_setting('share_scuttle') %}
<li> <li>
<a href="{{ craue_setting('scuttle_url') }}/bookmarks.php?action=add&amp;address={{ entry.url|url_encode }}&amp;title={{ entry.title|striptags|url_encode }}&amp;tags={{ entry.tags|join(',')|striptags|url_encode }}" target="_blank"> <a href="{{ craue_setting('scuttle_url') }}/bookmarks.php?action=add&amp;address={{ entry.url|url_encode }}&amp;title={{ entry.title|striptags|url_encode }}&amp;tags={{ entry.tags|join(',')|striptags|url_encode }}" target="_blank" title="scuttle" class="tool icon-image scuttle">
<i class="tool icon-image icon-image--scuttle" title="scuttle"></i>
<span>scuttle</span> <span>scuttle</span>
</a> </a>
</li> </li>
{% endif %} {% endif %}
{% if craue_setting('share_diaspora') %} {% if craue_setting('share_diaspora') %}
<li> <li>
<a href="{{ craue_setting('diaspora_url') }}/bookmarklet?url={{ entry.url|url_encode }}&amp;title={{ entry.title|striptags|url_encode }}&amp;notes=&amp;v=1&amp;noui=1&amp;jump=doclose" target="_blank"> <a href="{{ craue_setting('diaspora_url') }}/bookmarklet?url={{ entry.url|url_encode }}&amp;title={{ entry.title|striptags|url_encode }}&amp;notes=&amp;v=1&amp;noui=1&amp;jump=doclose" target="_blank" class="tool icon-image diaspora" title="diaspora">
<i class="tool icon-image icon-image--diaspora" title="diaspora"></i>
<span>diaspora*</span> <span>diaspora*</span>
</a> </a>
</li> </li>
{% endif %} {% endif %}
{% if craue_setting('share_unmark') %} {% if craue_setting('share_unmark') %}
<li> <li>
<a href="{{ craue_setting('unmark_url') }}/mark/add?url={{ entry.url|url_encode }}&amp;title={{entry.title|striptags|url_encode}}&amp;v=6" target="_blank"> <a href="{{ craue_setting('unmark_url') }}/mark/add?url={{ entry.url|url_encode }}&amp;title={{entry.title|striptags|url_encode}}&amp;v=6" target="_blank" class="tool icon-image unmark" title="unmark">
<i class="tool icon-image icon-image--unmark" title="unmark"></i>
<span>unmark.it</span> <span>unmark.it</span>
</a> </a>
</li> </li>
{% endif %} {% endif %}
{% if craue_setting('carrot') %} {% if craue_setting('carrot') %}
<li> <li>
<a href="https://secure.carrot.org/GiveAndGetBack.do?url={{ entry.url|url_encode }}&amp;title={{ entry.title|striptags|url_encode }}" target="_blank" title="carrot"> <a href="https://secure.carrot.org/GiveAndGetBack.do?url={{ entry.url|url_encode }}&amp;title={{ entry.title|striptags|url_encode }}" target="_blank" title="carrot" class="tool icon-image carrot">
<i class="tool icon-image icon-image--carrot"></i>
<span>Carrot</span> <span>Carrot</span>
</a> </a>
</li> </li>
{% endif %} {% endif %}
{% if craue_setting('share_mail') %} {% if craue_setting('share_mail') %}
<li> <li>
<a href="mailto:?subject={{ entry.title|striptags|url_encode }}&amp;body={{ entry.url|url_encode }}%20via%20@wallabagapp" title="{{ 'entry.view.left_menu.share_email_label'|trans }}" class="tool email icon icon-mail"> <a href="mailto:?subject={{ entry.title|striptags|url_encode }}&amp;body={{ entry.url|url_encode }}%20via%20@wallabagapp" title="{{ 'entry.view.left_menu.share_email_label'|trans }}" class="tool icon">
<i class="material-icons vertical-align-middle">mail</i>
<span>{{ 'entry.view.left_menu.share_email_label'|trans }}</span> <span>{{ 'entry.view.left_menu.share_email_label'|trans }}</span>
</a> </a>
</li> </li>
@ -220,7 +216,8 @@
<h1>{{ entry.title|striptags|raw }} <a href="{{ path('edit', { 'id': entry.id }) }}" title="{{ 'entry.view.edit_title'|trans }}">✎</a></h1> <h1>{{ entry.title|striptags|raw }} <a href="{{ path('edit', { 'id': entry.id }) }}" title="{{ 'entry.view.edit_title'|trans }}">✎</a></h1>
</header> </header>
<aside> <aside>
<ul class="tools"> <div class="tools">
<ul class="stats">
<li> <li>
{% include "@WallabagCore/themes/material/Entry/_reading_time.html.twig" with {'entry': entry} only %} {% include "@WallabagCore/themes/material/Entry/_reading_time.html.twig" with {'entry': entry} only %}
</li> </li>
@ -252,14 +249,15 @@
<i class="material-icons link">comment</i> <i class="material-icons link">comment</i>
{{ 'entry.view.annotations_on_the_entry'|transchoice(entry.annotations | length) }} {{ 'entry.view.annotations_on_the_entry'|transchoice(entry.annotations | length) }}
</li> </li>
<li id="list">
{% for tag in entry.tags %}
<div class="chip">
<a href="{{ path('tag_entries', {'slug': tag.slug}) }}">{{ tag.label }}</a> <a href="{{ path('remove_tag', { 'entry': entry.id, 'tag': tag.id }) }}"><i class="material-icons">delete</i></a>
</div>
{% endfor %}
</li>
</ul> </ul>
<ul class="tags">
{% for tag in entry.tags %}
<li class="chip">
<a href="{{ path('tag_entries', {'slug': tag.slug}) }}">{{ tag.label }}</a> <a href="{{ path('remove_tag', { 'entry': entry.id, 'tag': tag.id }) }}"><i class="material-icons vertical-align-middle">delete</i></a>
</li>
{% endfor %}
</ul>
</div>
<div class="input-field nav-panel-add-tag" style="display: none"> <div class="input-field nav-panel-add-tag" style="display: none">
{{ render(controller( "WallabagCoreBundle:Tag:addTagForm", { 'id': entry.id } )) }} {{ render(controller( "WallabagCoreBundle:Tag:addTagForm", { 'id': entry.id } )) }}

View file

@ -2,12 +2,14 @@
{% block css %} {% block css %}
{{ parent() }} {{ parent() }}
<link rel="stylesheet" href="{{ asset('bundles/wallabagcore/themes/material/css/style.min.css') }}" media="screen,projection,print"/> {% if not app.debug %}
<link rel="stylesheet" href="{{ asset('bundles/wallabagcore/material.css') }}">
{% endif %}
{% endblock %} {% endblock %}
{% block scripts %} {% block scripts %}
{{ parent() }} {{ parent() }}
<script src="{{ asset('bundles/wallabagcore/themes/material/js/material.min.js') }}"></script> <script src="{{ asset('bundles/wallabagcore/material' ~ (app.debug ? '.dev' : '') ~ '.js') }}"></script>
{% endblock %} {% endblock %}
{% block header %} {% block header %}
@ -116,12 +118,12 @@
</ul> </ul>
<div class="input-field nav-panel-search" style="display: none"> <div class="input-field nav-panel-search" style="display: none">
{{ render(controller("WallabagCoreBundle:Entry:searchForm", {'currentRoute': app.request.attributes.get('_route')})) }} {{ render(controller("WallabagCoreBundle:Entry:searchForm", {'currentRoute': app.request.attributes.get('_route')})) }}
<label for="search" class="active"><i class="material-icons search">search</i></label> <label for="search"><i class="material-icons search">search</i></label>
<i class="material-icons close">clear</i> <i class="material-icons close">clear</i>
</div> </div>
<div class="input-field nav-panel-add" style="display: none"> <div class="input-field nav-panel-add" style="display: none">
{{ render(controller("WallabagCoreBundle:Entry:addEntryForm")) }} {{ render(controller("WallabagCoreBundle:Entry:addEntryForm")) }}
<label for="add" class="active"><i class="material-icons add">add</i></label> <label for="add"><i class="material-icons add">add</i></label>
<i class="material-icons close">clear</i> <i class="material-icons close">clear</i>
</div> </div>
</div> </div>

File diff suppressed because one or more lines are too long

View file

@ -0,0 +1 @@
{"version":3,"sources":[],"names":[],"mappings":"","file":"baggy.css","sourceRoot":""}

File diff suppressed because one or more lines are too long

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Some files were not shown because too many files have changed in this diff Show more