Browse Source

further auth progress, responsive navbar and footer

Rafał Pitoń 10 years ago
parent
commit
7274fbe441
31 changed files with 1000 additions and 157 deletions
  1. 13 1
      docs/developers/settings.rst
  2. 21 0
      misago/core/migrations/0002_basic_settings.py
  3. 3 0
      misago/emberapp/app/components/forum-footer.js
  4. 23 0
      misago/emberapp/app/components/forum-navbar.js
  5. 18 6
      misago/emberapp/app/components/user-avatar.js
  6. 2 1
      misago/emberapp/app/components/user-nav.js
  7. 0 21
      misago/emberapp/app/controllers/index.js
  8. 63 5
      misago/emberapp/app/styles/misago/buttons.less
  9. 64 0
      misago/emberapp/app/styles/misago/dropdowns.less
  10. 1 3
      misago/emberapp/app/styles/misago/footer.less
  11. 2 0
      misago/emberapp/app/styles/misago/misago.less
  12. 41 0
      misago/emberapp/app/styles/misago/misc.less
  13. 187 18
      misago/emberapp/app/styles/misago/navbar.less
  14. 60 5
      misago/emberapp/app/styles/misago/variables.less
  15. 2 1
      misago/emberapp/app/templates/application.hbs
  16. 1 1
      misago/emberapp/app/templates/components/forms/login-form.hbs
  17. 30 32
      misago/emberapp/app/templates/components/forum-footer.hbs
  18. 153 0
      misago/emberapp/app/templates/components/forum-navbar.hbs
  19. 83 4
      misago/emberapp/app/templates/components/user-nav.hbs
  20. 30 10
      misago/emberapp/app/templates/index.hbs
  21. 145 16
      misago/emberapp/app/templates/navbar.hbs
  22. BIN
      misago/emberapp/public/misago/img/misago_logo.png
  23. BIN
      misago/emberapp/public/misago/img/site-icon.png
  24. BIN
      misago/emberapp/public/misago/img/site-logo.png
  25. 11 11
      misago/emberapp/tests/acceptance/error-toast-test.js
  26. 13 13
      misago/emberapp/tests/acceptance/login-test.js
  27. 8 8
      misago/emberapp/tests/acceptance/registration-test.js
  28. 1 1
      misago/emberapp/vendor/testutils/misago-preload-data.js
  29. 1 0
      misago/users/serializers/__init__.py
  30. 19 0
      misago/users/serializers/rank.py
  31. 5 0
      misago/users/serializers/user.py

+ 13 - 1
docs/developers/settings.rst

@@ -135,10 +135,22 @@ default_timezone
 Default timezone used by guests and newly registered users that haven't changed their timezone prefferences.
 Default timezone used by guests and newly registered users that haven't changed their timezone prefferences.
 
 
 
 
+forum_branding_display
+----------------------
+
+Controls branding's visibility in forum navbar.
+
+
+forum_branding_text
+-------------------
+
+Allows you to include text besides brand logo on your forum.
+
+
 forum_name
 forum_name
 ----------
 ----------
 
 
-Forum name, displayed in default templates forum navbar and in titles of pages.
+Forum name, displayed in titles of pages.
 
 
 
 
 forum_index_meta_description
 forum_index_meta_description

+ 21 - 0
misago/core/migrations/0002_basic_settings.py

@@ -48,6 +48,27 @@ def create_basic_settings_group(apps, schema_editor):
                     },
                     },
                 },
                 },
                 {
                 {
+                    'setting': 'forum_branding_display',
+                    'name': _("Display branding"),
+                    'description': _("Switch branding in forum's navbar."),
+                    'legend': _("Branding"),
+                    'value': True,
+                    'python_type': 'bool',
+                    'form_field': 'yesno',
+                    'is_public': True,
+                },
+                {
+                    'setting': 'forum_branding_text',
+                    'name': _("Branding text"),
+                    'description': _("Optional text displayed besides "
+                                     "brand image in navbar."),
+                    'value': "isago",
+                    'field_extra': {
+                        'max_length': 255
+                    },
+                    'is_public': True,
+                },
+                {
                     'setting': 'email_footer',
                     'setting': 'email_footer',
                     'name': _("E-mails footer"),
                     'name': _("E-mails footer"),
                     'description': _("Optional short message included "
                     'description': _("Optional short message included "

+ 3 - 0
misago/emberapp/app/components/forum-footer.js

@@ -1,6 +1,9 @@
 import Ember from 'ember';
 import Ember from 'ember';
 
 
 export default Ember.Component.extend({
 export default Ember.Component.extend({
+  tagName: 'footer',
+  classNames: 'site-footer',
+
   showTermsLink: function() {
   showTermsLink: function() {
     return this.get('settings.terms_of_service') || this.get('settings.terms_of_service_link');
     return this.get('settings.terms_of_service') || this.get('settings.terms_of_service_link');
   }.property('settings'),
   }.property('settings'),

+ 23 - 0
misago/emberapp/app/components/forum-navbar.js

@@ -0,0 +1,23 @@
+import Ember from 'ember';
+
+export default Ember.Component.extend({
+  classNames: 'navbar-spacer',
+
+  affixNavbar: function() {
+    // take navbar's height in document
+    this.$().height(this.$().height());
+
+    // affix navbar
+    this.$('.navbar').affix({
+      offset: {
+        top: this.$('.navbar').offset().top
+      }
+    });
+  }.on('didInsertElement'),
+
+  actions: {
+    showModal: function(template, model) {
+      this.modal.show(template, model);
+    }
+  }
+});

+ 18 - 6
misago/emberapp/app/components/user-avatar.js

@@ -3,15 +3,27 @@ import Ember from 'ember';
 export default Ember.Component.extend({
 export default Ember.Component.extend({
   tagName: 'img',
   tagName: 'img',
   classNames: 'user-avatar',
   classNames: 'user-avatar',
-  attributeBindings: ['src', 'alt'],
+  attributeBindings: ['src', 'alt', 'size:width', 'size:height'],
 
 
   size: 100,
   size: 100,
 
 
   src: function() {
   src: function() {
-    return '/user-avatar/' + this.get('size') + '/' + this.get('id') + '.png';
-  }.property('id', 'size'),
+    var src = Ember.$('base').attr('href') + 'user-avatar/';
 
 
-  alt: function() {
-    return '';
-  }.property()
+    if (this.get('user')) {
+      if (this.get('prefix') && this.get('token')) {
+        // special avatar source
+        src += this.get('prefix') + ':' + this.get('token') + '/';
+      } else {
+        // just avatar size
+        src += this.get('size') + '/';
+      }
+      return src + this.get('user') + '.png';
+    } else {
+      // just append avatar size to file to produce no-avatar placeholder
+      return src + this.get('size') + '.png';
+    }
+  }.property('user', 'size'),
+
+  alt: ''
 });
 });

+ 2 - 1
misago/emberapp/app/components/user-nav.js

@@ -1,7 +1,8 @@
 import Ember from 'ember';
 import Ember from 'ember';
 
 
 export default Ember.Component.extend({
 export default Ember.Component.extend({
-  classNames: ['user-nav', 'navbar-right'],
+  tagName: 'li',
+  classNames: ['user-menu', 'dropdown'],
 
 
   actions: {
   actions: {
     logout: function() {
     logout: function() {

+ 0 - 21
misago/emberapp/app/controllers/index.js

@@ -1,21 +0,0 @@
-import Ember from 'ember';
-
-export default Ember.Controller.extend({
-  actions: {
-    testInfo: function() {
-      this.toast.info(this.get('newFlash'));
-    },
-
-    testSuccess: function() {
-      this.toast.success(this.get('newFlash'));
-    },
-
-    testWarning: function() {
-      this.toast.warning(this.get('newFlash'));
-    },
-
-    testError: function() {
-      this.toast.error(this.get('newFlash'));
-    }
-  }
-});

+ 63 - 5
misago/emberapp/app/styles/misago/buttons.less

@@ -2,9 +2,43 @@
 // Buttons
 // Buttons
 // --------------------------------------------------
 // --------------------------------------------------
 
 
+// Mixin for styles
+.btn-outlined-style(@border, @bg, @color) {
+  &, &:visited {
+    background-color: transparent;
+    border-color: @border;
 
 
-// Double border size on default and lg buttons
-.btn {
+    color: @border;
+  }
+
+  &:hover, &:focus {
+    background-color: fadeOut(@bg, 60%);
+    border-color: @border;
+
+    color: @color;
+  }
+
+  &:active {
+    background-color: darken(@bg, 10%);
+    border-color: @border;
+    .box-shadow(none);
+
+    color: @color;
+  }
+
+  &.disabled {
+    &, &:visited, &:hover, &:focus, &:active {
+      background-color: transparent;
+      border-color: desaturate(@border, 50%);
+
+      color: desaturate(@border, 50%);
+    }
+  }
+}
+
+
+// Outlined button
+.btn-outlined {
   border-width: 2px;
   border-width: 2px;
 
 
   .button-size(@padding-base-vertical - 1; @padding-base-horizontal; @font-size-base; @line-height-base; @border-radius-base);
   .button-size(@padding-base-vertical - 1; @padding-base-horizontal; @font-size-base; @line-height-base; @border-radius-base);
@@ -22,11 +56,35 @@
     border-width: 1px;
     border-width: 1px;
     .button-size(@padding-xs-vertical; @padding-xs-horizontal; @font-size-small; @line-height-small; @border-radius-small);
     .button-size(@padding-xs-vertical; @padding-xs-horizontal; @font-size-small; @line-height-small; @border-radius-small);
   }
   }
-}
 
 
+  // Outline varieties for buttons
+  &.btn-default, &.btn-primary, &.btn-success, &.btn-info, &.btn-warning, &.btn-danger {
+    &, &:visited {
+      background-color: transparent;
+    }
+  }
+
+  &.btn-primary {
+    .btn-outlined-style(@btn-primary-border, @btn-primary-bg, @btn-primary-color);
+  }
+
+  &.btn-success {
+    .btn-outlined-style(@btn-success-border, @btn-success-bg, @btn-success-color);
+  }
+
+  &.btn-info {
+    .btn-outlined-style(@btn-info-border, @btn-info-bg, @btn-info-color);
+  }
+
+  &.btn-warning {
+    .btn-outlined-style(@btn-warning-border, @btn-warning-bg, @btn-warning-color);
+  }
+
+  &.btn-danger {
+    .btn-outlined-style(@btn-danger-border, @btn-danger-bg, @btn-danger-color);
+  }
 
 
-// Extra states for default btn
-.btn {
+  // Extra states for default btn
   &.btn-default {
   &.btn-default {
     &:hover,
     &:hover,
     &:focus,
     &:focus,

+ 64 - 0
misago/emberapp/app/styles/misago/dropdowns.less

@@ -0,0 +1,64 @@
+//
+// Dropdowns
+// --------------------------------------------------
+
+
+// Dropdowns style
+.dropdown-menu {
+  border-radius: @dropdown-border-radius;
+  .box-shadow(@dropdown-shadow);
+}
+
+
+.dropdown-menu > li > a > .badge {
+  float: right;
+}
+
+.dropdown-space {
+  padding: 7px 20px;
+}
+
+.dropdown-footer {
+  background: @dropdown-footer-bg;
+  border-top: 1px solid @dropdown-footer-border;
+  border-radius: 0px 0px @dropdown-border-radius @dropdown-border-radius;
+  padding: 7px 20px;
+}
+
+
+// User dropdown
+.user-dropdown {
+  width: 300px;
+  padding: 0px;
+
+  .user-preview, .guest-preview {
+    border-bottom: 1px solid @dropdown-divider-bg;
+    margin-bottom: 8px;
+    padding: 12px 20px;
+
+    .editable-avatar {
+      margin-right: 4px;
+    }
+
+    .row {
+      margin-top: @line-height-computed * 1.3;
+
+      div:first-child {
+        padding-right: 4px;
+      }
+
+      div:last-child {
+        padding-left: 4px;
+      }
+    }
+  }
+
+  .guest-preview {
+    border-bottom: 0px;
+    margin-bottom: 4px;
+  }
+
+  .dropdown-footer {
+    margin-top: 8px;
+  }
+}

+ 1 - 3
misago/emberapp/app/styles/misago/footer.less

@@ -4,7 +4,7 @@
 
 
 
 
 .site-footer {
 .site-footer {
-  margin-top: @line-height-computed * 1.5;
+  margin-top: @line-height-computed;
   padding-bottom: @line-height-computed * 1.5;
   padding-bottom: @line-height-computed * 1.5;
 
 
   color: @footer-color;
   color: @footer-color;
@@ -40,8 +40,6 @@
 
 
   /* Big devices (tablets, 768px and up) */
   /* Big devices (tablets, 768px and up) */
   @media (min-width: @screen-sm-min) {
   @media (min-width: @screen-sm-min) {
-    margin-top: @line-height-computed * 2;
-    padding-top: @line-height-computed * 1.5;
     overflow: auto;
     overflow: auto;
 
 
     text-align: left;
     text-align: left;

+ 2 - 0
misago/emberapp/app/styles/misago/misago.less

@@ -1,5 +1,6 @@
 // Components
 // Components
 @import "buttons.less";
 @import "buttons.less";
+@import "dropdowns.less";
 @import "toast-message.less";
 @import "toast-message.less";
 @import "footer.less";
 @import "footer.less";
 @import "forms.less";
 @import "forms.less";
@@ -8,6 +9,7 @@
 @import "navbar.less";
 @import "navbar.less";
 @import "page-header.less";
 @import "page-header.less";
 @import "typo.less";
 @import "typo.less";
+@import "misc.less";
 
 
 // Pages
 // Pages
 @import "errorpages.less";
 @import "errorpages.less";

+ 41 - 0
misago/emberapp/app/styles/misago/misc.less

@@ -0,0 +1,41 @@
+//
+// Misc utils
+// --------------------------------------------------
+
+
+
+// Avatar with "edit" button
+.editable-avatar {
+  background: none;
+  border-radius: @border-radius-base;
+
+  margin: 0px;
+  padding: 0px;
+
+  position: relative;
+  overflow: hidden;
+
+  .help {
+    background: fadeOut(#000, 30%);
+    border-radius: 0px;
+    display: block;
+    margin: 0px;
+    padding: 4px 0px;
+    width: 100%;
+
+    .opacity(0.6);
+
+    position: absolute;
+    bottom: 0px;
+
+    color: #fff;
+    font-size: @font-size-small;
+    text-shadow: 1px 1px 0px #000;
+  }
+
+  &:hover, &:focus {
+    .help {
+      .opacity(1);
+    }
+  }
+}

+ 187 - 18
misago/emberapp/app/styles/misago/navbar.less

@@ -3,52 +3,221 @@
 // --------------------------------------------------
 // --------------------------------------------------
 
 
 
 
+// Affixed navbar
+.navbar-spacer {
+  margin-bottom: @line-height-computed;
+
+  .navbar-primary {
+    border-bottom-width: 1px;
+    margin: 0px;
+
+    &.affix {
+      .box-shadow(0px 0px 3px fadeOut(#333, 70%));
+
+      width: 100%;
+      top: 0px;
+    }
+  }
+}
+
+
 // Navbar brand
 // Navbar brand
 .navbar-primary {
 .navbar-primary {
-  border-bottom-width: 1px;
-
   .navbar-brand {
   .navbar-brand {
     font-size: @font-size-large * 1.2;
     font-size: @font-size-large * 1.2;
+    font-weight: @weight-light;
 
 
     img {
     img {
-      border-radius: @border-radius-small;
       display: inline-block;
       display: inline-block;
-      height: @navbar-height - @navbar-padding-vertical * 2 + 3px;
+      height: @navbar-brand-height;
+      margin: ((@line-height-computed - @navbar-brand-height) / 2) 0px;
 
 
       position: relative;
       position: relative;
-      bottom: 2px;
+      bottom: 3px;
     }
     }
   }
   }
 }
 }
 
 
 
 
-// Navbar nav
+// Navbar navs
 .navbar-primary {
 .navbar-primary {
   .navbar-nav {
   .navbar-nav {
+    float: left;
 
 
-    // Make icons bigger
     &>li {
     &>li {
+      float: left;
+
       &>a {
       &>a {
-        .fa, .glyphicon {
-          position: relative;
-          top: (@font-size-large - @font-size-base) / 2 + 1px;
+        // Scale links up
+        font-size: @navbar-link-size;
+
+        // We don't use .active states in navbar
+        &:active, &:focus {
+          color: @navbar-default-link-active-color;
+        }
 
 
-          font-size: @font-size-large;
+        // Align badges to glyhps
+        &>.badge {
+          vertical-align: inherit;
+          margin: (@line-height-computed / -2) 0px;
+        }
+
+        &>.glyphicon {
+          position: relative;
+          top: 4px;
         }
         }
       }
       }
     }
     }
+  }
+}
+
 
 
-    // Uncollapse the nav
+// User Menu
+.navbar-primary {
+  .navbar-user-nav {
     float: right;
     float: right;
-    margin: 0;
 
 
-    > li {
-      float: left;
-      > a {
-        padding-top:    @navbar-padding-vertical;
-        padding-bottom: @navbar-padding-vertical;
+    .btn-success {
+      position: relative;
+      top: 1px;
+    }
+  }
+
+  .user-menu {
+    .dropdown-toggle {
+      .fa {
+        font-size: @font-size-base;
       }
       }
+
+      img {
+        border-radius: @avatar-radius-small;
+        margin: (@line-height-computed / -2) 0px;
+
+        width: 28px;
+        height: 28px;
+      }
+    }
+  }
+}
+
+
+// Guest Menu
+.navbar-primary {
+  .navbar-guest-nav {
+    float: right;
+
+    .btn {
+      position: relative;
+      top: 1px;
     }
     }
+  }
+}
+
+
+// Dropdowns
+.navbar-static-top {
+  & .navbar-nav > li > .dropdown-menu {
+    border-radius: @dropdown-border-radius;
+  }
+}
 
 
+
+// Compact nav
+@media (max-width: @screen-sm-max) {
+  .navbar-primary {
+    min-height: @navbar-compact-height;
+  }
+}
+
+.navbar-primary {
+  .navbar-compact-nav {
+    margin: 0px;
+    float: none;
+    width: 100%;
+
+    &>li {
+      &>a {
+        padding: @navbar-compact-padding-vertical 0px;
+        height: @navbar-compact-height;
+
+        text-align: center;
+
+        // Align glyphs to middle of height
+        .glyphicon {
+          position: static;
+
+          font-size: 20px;
+        }
+
+        // Align images
+        img {
+          width: 28px;
+          margin: ((@line-height-computed - 28) / 2) 0px;
+
+          position: relative;
+          bottom: 2px;
+        }
+
+        // Custom touched style
+        &:active {
+          background-color: @navbar-compact-link-active-bg;
+
+          color: @navbar-compact-link-active-color;
+        }
+      }
+    }
+
+    .dropdown {
+      &.open .dropdown-toggle {
+        background-color: @navbar-compact-link-active-bg;
+
+        color: @navbar-compact-link-active-color;
+      }
+
+      .dropdown-menu {
+        position: absolute;
+        float: right;
+        width: 300px;
+        margin-top: 2px;
+        background-color: @dropdown-bg;
+        border: 1px solid @dropdown-fallback-border; // IE8 fallback
+        border: 1px solid @dropdown-border;
+        border-radius: @dropdown-border-radius;
+        .box-shadow(@dropdown-shadow);
+      }
+    }
+
+    // Even widths
+    &.with-4-links {
+      &>li {
+        width: 25%;
+      }
+    }
+
+    &.with-5-links {
+      &>li {
+        width: 20%;
+      }
+    }
+
+    &.with-6-links {
+      &>li {
+        width: 16%;
+
+        &:first-child, &:last-child {
+          width: 18%;
+        }
+      }
+    }
+
+    &.with-7-links {
+      &>li {
+        width: 14%;
+
+        &:first-child, &:last-child {
+          width: 15%;
+        }
+      }
+    }
   }
   }
 }
 }

+ 60 - 5
misago/emberapp/app/styles/misago/variables.less

@@ -14,7 +14,7 @@
 @gray-light:             lighten(@gray-base, 46.7%); // #777
 @gray-light:             lighten(@gray-base, 46.7%); // #777
 @gray-lighter:           lighten(@gray-base, 93.5%); // #eee
 @gray-lighter:           lighten(@gray-base, 93.5%); // #eee
 
 
-@brand-info:             #ff5722; // misago uses info state for accents
+@brand-info:             #e66a5d; // misago uses info state for accents
 
 
 @brand-primary:          #3498db;
 @brand-primary:          #3498db;
 @brand-success:          #2ecc71;
 @brand-success:          #2ecc71;
@@ -52,6 +52,11 @@
 @state-clicked:         @brand-primary;
 @state-clicked:         @brand-primary;
 
 
 
 
+//** Avatar radius
+@avatar-radius:             8px;
+@avatar-radius-small:       4px;
+
+
 //== Typography
 //== Typography
 //
 //
 //## headings
 //## headings
@@ -61,12 +66,29 @@
 @headings-color:          lighten(@text-color, 8%);;
 @headings-color:          lighten(@text-color, 8%);;
 
 
 
 
+//== Badges
+//
+//##
+
+@badge-color:                 #fff;
+//** Linked badge text color on hover
+@badge-link-hover-color:      #fff;
+@badge-bg:                    @brand-info;
+
+//** Badge text color in active nav link
+@badge-active-color:          @link-color;
+//** Badge background color in active nav link
+@badge-active-bg:             #fff;
+
+@badge-font-weight:           @weight-light;
+
+
 //== Navbar
 //== Navbar
 //
 //
 //##
 //##
 
 
 // Basics of a navbar
 // Basics of a navbar
-@navbar-height:                    50px;
+@navbar-height:                    46px;
 @navbar-margin-bottom:             @line-height-computed;
 @navbar-margin-bottom:             @line-height-computed;
 @navbar-border-radius:             @border-radius-base;
 @navbar-border-radius:             @border-radius-base;
 @navbar-padding-horizontal:        floor((@grid-gutter-width / 2));
 @navbar-padding-horizontal:        floor((@grid-gutter-width / 2));
@@ -78,16 +100,26 @@
 @navbar-default-border:            @gray-lighter;
 @navbar-default-border:            @gray-lighter;
 
 
 // Navbar links
 // Navbar links
-@navbar-default-link-color:                darken(@gray-lighter, 20%);
-@navbar-default-link-hover-color:          @gray-light;
+@navbar-link-size:                         @font-size-base + 2px;
+
+@navbar-default-link-color:                @site-link-color;
+@navbar-default-link-hover-color:          @site-link-hover-color;
 @navbar-default-link-hover-bg:             transparent;
 @navbar-default-link-hover-bg:             transparent;
-@navbar-default-link-active-color:         @gray-darker;
+@navbar-default-link-active-color:         @site-link-active-color;
 @navbar-default-link-active-bg:            transparent;
 @navbar-default-link-active-bg:            transparent;
 
 
+@navbar-compact-link-active-color:         @navbar-default-bg;
+@navbar-compact-link-active-bg:            @site-link-active-color;
+
 // Navbar brand label
 // Navbar brand label
 @navbar-default-brand-color:               @headings-color;
 @navbar-default-brand-color:               @headings-color;
 @navbar-default-brand-hover-color:         @headings-color;
 @navbar-default-brand-hover-color:         @headings-color;
 
 
+@navbar-brand-height:                      @navbar-height - @navbar-padding-vertical * 2 + 3px;
+
+// Compact navbar, used on mobiles
+@navbar-compact-height:                    40px;
+@navbar-compact-padding-vertical:          ((@navbar-compact-height - @line-height-computed) / 2);
 
 
 //== Site Footer
 //== Site Footer
 //
 //
@@ -221,3 +253,26 @@
 
 
 @panel-form-footer-bg:              @panel-form-bg;
 @panel-form-footer-bg:              @panel-form-bg;
 @panel-form-footer-border:          darken(@panel-form-bg, 10%);
 @panel-form-footer-border:          darken(@panel-form-bg, 10%);
+
+
+//== Dropdowns
+//
+//** Dropdown radius and shadow
+@dropdown-border-radius:            @border-radius-base;
+@dropdown-shadow:                   0px 0px 0px 3px fadeOut(@gray, 50%);
+
+//** Dropdown link text color.
+@dropdown-link-color:            @site-link-color;
+//** Hover color for dropdown links.
+@dropdown-link-hover-color:      @site-link-hover-color;
+//** Hover background for dropdown links.
+@dropdown-link-hover-bg:         transparent;
+
+//** Active dropdown menu item text color.
+@dropdown-link-active-color:     @site-link-active-color;
+//** Active dropdown menu item background color.
+@dropdown-link-active-bg:        transparent;
+
+//** Dropdown footer bg and border
+@dropdown-footer-border:         darken(@dropdown-bg, 10%);
+@dropdown-footer-bg:             darken(@dropdown-bg, 3%);

+ 2 - 1
misago/emberapp/app/templates/application.hbs

@@ -1,4 +1,4 @@
-{{render "navbar"}}
+{{forum-navbar}}
 {{toast-message}}
 {{toast-message}}
 
 
 <div class="main-outlet">
 <div class="main-outlet">
@@ -6,6 +6,7 @@
 </div>
 </div>
 
 
 {{forum-footer}}
 {{forum-footer}}
+
 <div class="modal fade" id="appModal" tabindex="-1" role="dialog" aria-labelledby="appModalLabel" aria-hidden="true">
 <div class="modal fade" id="appModal" tabindex="-1" role="dialog" aria-labelledby="appModalLabel" aria-hidden="true">
   {{outlet "modal"}}
   {{outlet "modal"}}
 </div>
 </div>

+ 1 - 1
misago/emberapp/app/templates/components/forms/login-form.hbs

@@ -29,7 +29,7 @@
     {{/if}}
     {{/if}}
   {{/if}}
   {{/if}}
 
 
-  {{#close-modal-button class="btn btn-block btn-default" goto="forgotten-password"}}
+  {{#close-modal-button class="btn btn-block btn-outlined btn-default" goto="forgotten-password"}}
     {{gettext "Forgot password?"}}
     {{gettext "Forgot password?"}}
   {{/close-modal-button}}
   {{/close-modal-button}}
 
 

+ 30 - 32
misago/emberapp/app/templates/components/forum-footer.hbs

@@ -1,39 +1,37 @@
-<footer class="site-footer">
-  <div class="container">
-    <div class="footer-content">
+<div class="container">
+  <div class="footer-content">
 
 
-      {{#if hasContent}}
-      <ul class="list-inline footer-nav">
-        {{#if settings.forum_footnote}}
-          <li class="site-footnote">
-            {{settings.forum_footnote}}
-          </li>
-        {{/if}}
-        {{#if showTermsLink}}
-          <li>
-          {{#if settings.terms_of_service_link }}
-            <a href="{{unbound settings.terms_of_service_link}}">{{gettext "Terms of service" }}</a>
-          {{else}}
-            {{#link-to 'terms-of-service'}}{{gettext "Terms of service" }}{{/link-to}}
-          {{/if}}
-          </li>
+    {{#if hasContent}}
+    <ul class="list-inline footer-nav">
+      {{#if settings.forum_footnote}}
+        <li class="site-footnote">
+          {{settings.forum_footnote}}
+        </li>
+      {{/if}}
+      {{#if showTermsLink}}
+        <li>
+        {{#if settings.terms_of_service_link }}
+          <a href="{{unbound settings.terms_of_service_link}}">{{gettext "Terms of service" }}</a>
+        {{else}}
+          {{#link-to 'terms-of-service'}}{{gettext "Terms of service" }}{{/link-to}}
         {{/if}}
         {{/if}}
-        {{#if showPrivacyLink}}
-          <li>
-          {{#if settings.privacy_policy_link }}
-            <a href="{{unbound settings.privacy_policy_link}}">{{gettext "Privacy policy" }}</a>
-          {{else}}
-            {{#link-to 'privacy-policy'}}{{gettext "Privacy policy" }}{{/link-to}}
-          {{/if}}
-          </li>
+        </li>
+      {{/if}}
+      {{#if showPrivacyLink}}
+        <li>
+        {{#if settings.privacy_policy_link }}
+          <a href="{{unbound settings.privacy_policy_link}}">{{gettext "Privacy policy" }}</a>
+        {{else}}
+          {{#link-to 'privacy-policy'}}{{gettext "Privacy policy" }}{{/link-to}}
         {{/if}}
         {{/if}}
-      </ul>
+        </li>
       {{/if}}
       {{/if}}
+    </ul>
+    {{/if}}
 
 
-      <a href="http://misago-project.org" class="misago-branding">
-        powered by <strong>misago</strong>
-      </a>
+    <a href="http://misago-project.org" class="misago-branding">
+      powered by <strong>misago</strong>
+    </a>
 
 
-    </div>
   </div>
   </div>
-</footer>
+</div>

+ 153 - 0
misago/emberapp/app/templates/components/forum-navbar.hbs

@@ -0,0 +1,153 @@
+<nav class="navbar navbar-primary navbar-default navbar-static-top" role="navigation">
+  <div class="container">
+
+    {{#if settings.forum_branding_display}}
+      {{#link-to 'index' class="navbar-brand hidden-xs hidden-sm"}}
+        <img src="{{unbound staticUrl}}misago/img/site-logo.png" alt="">
+        {{#if settings.forum_branding_text}}
+          <span class="hidden-xs hidden-sm">{{settings.forum_branding_text}}</span>
+        {{/if}}
+      {{/link-to}}
+    {{/if}}
+
+    <ul class="nav navbar-nav hidden-xs hidden-sm">
+      <li>
+        <a href="#">
+          {{gettext "Threads"}}
+        </a>
+      </li>
+      <li>
+        <a href="#">
+          {{gettext "Forums"}}
+        </a>
+      </li>
+      <li>
+        <a href="#">
+          {{gettext "Feeds"}}
+        </a>
+      </li>
+      <li>
+        <a href="#">
+          {{gettext "Users"}}
+        </a>
+      </li>
+      <li>
+        <a href="#">
+          {{gettext "Search"}}
+        </a>
+      </li>
+    </ul>
+
+    {{#if auth.isAuthenticated}}
+    <ul class="nav navbar-nav navbar-user-nav hidden-xs hidden-sm">
+      <li class="">
+        <a href="#">
+          <span class="fa fa-exclamation-triangle fa-lg"></span>
+          <span class="badge">132</span>
+        </a>
+      </li>
+      <li class="user-notices dropdown">
+        <a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false">
+          <span class="fa fa-bell-o fa-lg"></span>
+          <span class="badge">132</span>
+        </a>
+        <ul class="dropdown-menu" role="menu">
+          <li><a href="#">Action</a></li>
+          <li><a href="#">Another action</a></li>
+          <li><a href="#">Something else here</a></li>
+          <li class="divider"></li>
+          <li><a href="#">Separated link</a></li>
+        </ul>
+      </li>
+      {{user-nav}}
+      <li>
+        <button type="button" class="btn btn-outlined btn-success navbar-btn">
+          <span class="glyphicon glyphicon-comment"></span>
+          {{gettext "Start thread"}}
+        </button>
+      </li>
+    </ul>
+    {{else}}
+    <div class="navbar-guest-nav hidden-xs hidden-sm">
+      <button type="button" class="btn btn-outlined btn-default navbar-btn" {{action "showModal" "login"}}>
+        {{gettext "Sign in"}}
+      </button>
+
+      {{#register-button class="btn btn-outlined btn-success navbar-btn"}}
+        {{gettext "Register account"}}
+      {{/register-button}}
+    </div>
+    {{/if}}
+  </div><!-- /full navbar -->
+
+  <ul class="nav navbar-nav navbar-compact-nav hidden-md hidden-lg {{if settings.forum_branding_display "with-7-links" "with-6-links"}}">
+    {{#if settings.forum_branding_display}}
+    <li class="compact-brand">
+      <a href="#">
+        <img src="{{unbound staticUrl}}misago/img/site-icon.png" alt="">
+      </a>
+    </li>
+    {{/if}}
+    <li>
+      <a href="#">
+        <span class="glyphicon glyphicon-comment"></span>
+      </a>
+    </li>
+    <li>
+      <a href="#">
+        <span class="glyphicon glyphicon-th-list"></span>
+      </a>
+    </li>
+    <li>
+      <a href="#">
+        <span class="glyphicon glyphicon-heart-empty"></span>
+      </a>
+    </li>
+    <li>
+      <a href="#">
+        <span class="glyphicon glyphicon-user"></span>
+      </a>
+    </li>
+    <li>
+      <a href="#">
+        <span class="glyphicon glyphicon-search"></span>
+      </a>
+    </li>
+    {{#if auth.isAuthenticated}}
+    {{user-nav}}
+    {{else}}
+    <li class="user-menu dropdown">
+      <a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false">
+        {{user-avatar size=28}}
+      </a>
+      <ul class="dropdown-menu user-dropdown dropdown-menu-right" role="menu">
+        <li class="guest-preview">
+
+          <div class="media">
+            <div class="media-body">
+
+              <h4 class="media-heading">{{gettext "You are browsing as guest."}}</h4>
+
+              <div class="row">
+                <div class="col-xs-6">
+                  <button type="button" class="btn btn-outlined btn-default btn-block btn-sm" {{action "showModal" "login"}}>
+                    {{gettext "Sign in"}}
+                  </button>
+                </div>
+                <div class="col-xs-6">
+                  {{#register-button class="btn btn-outlined btn-success btn-block btn-sm"}}
+                    {{gettext "Register account"}}
+                  {{/register-button}}
+                </div>
+              </div>
+
+            </div>
+          </div>
+
+        </li>
+      </ul>
+    </li>
+    {{/if}}
+  </ul>
+  <!-- /.compact navbar -->
+</nav>

+ 83 - 4
misago/emberapp/app/templates/components/user-nav.hbs

@@ -1,4 +1,83 @@
-<p class="navbar-text">
-  {{user-avatar id=auth.user.id size=200}}
-  {{auth.user.username}}
-</p>
+<a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false">
+  {{user-avatar user=auth.user.id size=28}}
+  <span class="fa fa-bars hidden-xs hidden-sm"></span>
+</a>
+<ul class="dropdown-menu user-dropdown dropdown-menu-right" role="menu">
+  <li class="user-preview">
+
+    <div class="media">
+      <div class="media-left">
+
+        <button type="button" class="btn editable-avatar">
+          {{user-avatar user=auth.user.id size=100}}
+          <div class="help">
+            {{gettext "Change avatar"}}
+          </div>
+        </button>
+
+      </div>
+      <div class="media-body">
+
+        <h4 class="media-heading">{{auth.user.username}}</h4>
+
+        <p class="text-muted">
+          {{auth.user.full_title}}
+        </p>
+
+        <div class="row">
+          <div class="col-xs-6">
+            <button type="button" class="btn btn-outlined btn-default btn-block btn-sm">
+              {{gettext "Profile"}}
+            </button>
+          </div>
+          <div class="col-xs-6">
+            <button type="button" class="btn btn-outlined btn-default btn-block btn-sm">
+              {{gettext "Options"}}
+            </button>
+          </div>
+        </div>
+
+      </div>
+    </div>
+
+  </li>
+  <li class="dropdown-space hidden-md hidden-lg">
+    <button type="button" class="btn btn-outlined btn-success btn-block">
+      <span class="glyphicon glyphicon-comment"></span>
+      {{gettext "Start thread"}}
+    </button>
+  </li>
+  <li class="divider hidden-md hidden-lg"></li>
+  <li>
+    <a href="#">
+      <span class="fa fa-exclamation-triangle fa-fw"></span>
+      {{gettext "Reports"}}
+      <span class="badge">132</span>
+    </a>
+  </li>
+  <li>
+    <a href="#">
+      <span class="fa fa-bell-o fa-fw"></span>
+      {{gettext "Notifications"}}
+      <span class="badge">132</span>
+    </a>
+  </li>
+  <li>
+    <a href="#">
+      <span class="fa fa-inbox fa-fw"></span>
+      {{gettext "Private threads"}}
+      <span class="badge">132</span>
+    </a>
+  </li>
+  <li>
+    <a href="#">
+      <span class="fa fa-bookmark fa-fw"></span>
+      {{gettext "Subscriptions"}}
+    </a>
+  </li>
+  <li class="dropdown-footer">
+    <button type="button" class="btn btn-outlined btn-default btn-block" {{action "logout"}}>
+      {{gettext "Log out"}}
+    </button>
+  </li>
+</ul>

+ 30 - 10
misago/emberapp/app/templates/index.hbs

@@ -1,20 +1,40 @@
 <div class="container">
 <div class="container">
   <h1>Welcome to Ember.js!</h1>
   <h1>Welcome to Ember.js!</h1>
-  <p class="lead">IndexController renders index.hbs template!</p>
+
+  <p class="lead">
+    Lorem ipsum dolor met sit amet elit.
+  </p>
+
   <p class="lead">
   <p class="lead">
-    Special pages: {{#link-to 'loading'}}Loading{{/link-to}}, {{#link-to 'error-0'}}Connection lost{{/link-to}}, {{#link-to 'error-404'}}Error 404{{/link-to}}.
+    Si vis pacem para bellum.
   </p>
   </p>
 
 
-  <hr>
+  <p class="lead">
+    Lorem ipsum dolor met sit amet elit.
+  </p>
 
 
-  <h2>{{gettext "Test %(msg)s Message" msg=(gettext "Flash")}}</h2>
+  <p class="lead">
+    Lorem ipsum dolor met sit amet elit.
+  </p>
+
+  <p class="lead">
+    Lorem ipsum dolor met sit amet elit.
+  </p>
 
 
-  <p>
-    {{input class="testinput" type="text" value=newFlash}}
-    <button class="btn btn-primary" {{action "testInfo"}}>Info</button>
-    <button class="btn btn-success" {{action "testSuccess"}}>Success</button>
-    <button class="btn btn-warning" {{action "testWarning"}}>Warning</button>
-    <button class="btn btn-danger" {{action "testError"}}>Error</button>
+  <p class="lead">
+    Lorem ipsum dolor met sit amet elit.
+  </p>
+
+  <p class="lead">
+    Lorem ipsum dolor met sit amet elit.
+  </p>
+
+  <p class="lead">
+    Lorem ipsum dolor met sit amet elit.
+  </p>
+
+  <p class="lead">
+    Lorem ipsum dolor met sit amet elit.
   </p>
   </p>
 
 
 </div>
 </div>

+ 145 - 16
misago/emberapp/app/templates/navbar.hbs

@@ -1,24 +1,153 @@
 <nav class="navbar navbar-primary navbar-default navbar-static-top" role="navigation">
 <nav class="navbar navbar-primary navbar-default navbar-static-top" role="navigation">
-  <div class="container">
+<div class="container">
 
 
-    {{#link-to 'index' class="navbar-brand"}}
-      <img src="{{unbound staticUrl}}misago/img/misago_logo.png" alt="">
-      <span>{{settings.forum_name}}</span>
+  {{#if settings.forum_branding_display}}
+    {{#link-to 'index' class="navbar-brand hidden-xs hidden-sm"}}
+      <img src="{{unbound staticUrl}}misago/img/site-logo.png" alt="">
+      {{#if settings.forum_branding_text}}
+        <span class="hidden-xs hidden-sm">{{settings.forum_branding_text}}</span>
+      {{/if}}
     {{/link-to}}
     {{/link-to}}
+  {{/if}}
 
 
-    {{#if auth.isAuthenticated}}
-      {{user-nav}}
-    {{else}}
-    <div class="guest-nav navbar-right">
-      <button type="button" class="btn btn-default btn-login navbar-btn btn-sm" {{action "showModal" "login"}}>
-        {{gettext "Sign in"}}
+  <ul class="nav navbar-nav hidden-xs hidden-sm">
+    <li>
+      <a href="#">
+        {{gettext "Threads"}}
+      </a>
+    </li>
+    <li>
+      <a href="#">
+        {{gettext "Forums"}}
+      </a>
+    </li>
+    <li>
+      <a href="#">
+        {{gettext "Feeds"}}
+      </a>
+    </li>
+    <li>
+      <a href="#">
+        {{gettext "Users"}}
+      </a>
+    </li>
+    <li>
+      <a href="#">
+        {{gettext "Search"}}
+      </a>
+    </li>
+  </ul>
+
+  {{#if auth.isAuthenticated}}
+  <ul class="nav navbar-nav navbar-user-nav hidden-xs hidden-sm">
+    <li class="">
+      <a href="#">
+        <span class="fa fa-exclamation-triangle fa-lg"></span>
+        <span class="badge">132</span>
+      </a>
+    </li>
+    <li class="user-notices dropdown">
+      <a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false">
+        <span class="fa fa-bell-o fa-lg"></span>
+        <span class="badge">132</span>
+      </a>
+      <ul class="dropdown-menu" role="menu">
+        <li><a href="#">Action</a></li>
+        <li><a href="#">Another action</a></li>
+        <li><a href="#">Something else here</a></li>
+        <li class="divider"></li>
+        <li><a href="#">Separated link</a></li>
+      </ul>
+    </li>
+    {{user-nav}}
+    <li>
+      <button type="button" class="btn btn-outlined btn-success navbar-btn">
+        <span class="glyphicon glyphicon-comment"></span>
+        {{gettext "Start thread"}}
       </button>
       </button>
+    </li>
+  </ul>
+  {{else}}
+  <div class="navbar-guest-nav hidden-xs hidden-sm">
+    <button type="button" class="btn btn-outlined btn-default navbar-btn" {{action "showModal" "login"}}>
+      {{gettext "Sign in"}}
+    </button>
+
+    {{#register-button class="btn btn-outlined btn-success navbar-btn"}}
+      {{gettext "Register account"}}
+    {{/register-button}}
+  </div>
+  {{/if}}
+</div><!-- /full navbar -->
+
+<ul class="nav navbar-nav navbar-compact-nav hidden-md hidden-lg {{if settings.forum_branding_display "with-7-links" "with-6-links"}}">
+  {{#if settings.forum_branding_display}}
+  <li class="compact-brand">
+    <a href="#">
+      <img src="{{unbound staticUrl}}misago/img/site-icon.png" alt="">
+    </a>
+  </li>
+  {{/if}}
+  <li>
+    <a href="#">
+      <span class="glyphicon glyphicon-comment"></span>
+    </a>
+  </li>
+  <li>
+    <a href="#">
+      <span class="glyphicon glyphicon-th-list"></span>
+    </a>
+  </li>
+  <li>
+    <a href="#">
+      <span class="glyphicon glyphicon-heart-empty"></span>
+    </a>
+  </li>
+  <li>
+    <a href="#">
+      <span class="glyphicon glyphicon-user"></span>
+    </a>
+  </li>
+  <li>
+    <a href="#">
+      <span class="glyphicon glyphicon-search"></span>
+    </a>
+  </li>
+  {{#if auth.isAuthenticated}}
+  {{user-nav}}
+  {{else}}
+  <li class="user-menu dropdown">
+    <a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-expanded="false">
+      {{user-avatar size=28}}
+    </a>
+    <ul class="dropdown-menu user-dropdown dropdown-menu-right" role="menu">
+      <li class="guest-preview">
+
+        <div class="media">
+          <div class="media-body">
+
+            <h4 class="media-heading">{{gettext "You are browsing as guest."}}</h4>
+
+            <div class="row">
+              <div class="col-xs-6">
+                <button type="button" class="btn btn-outlined btn-default btn-block btn-sm" {{action "showModal" "login"}}>
+                  {{gettext "Sign in"}}
+                </button>
+              </div>
+              <div class="col-xs-6">
+                {{#register-button class="btn btn-outlined btn-success btn-block btn-sm"}}
+                  {{gettext "Register account"}}
+                {{/register-button}}
+              </div>
+            </div>
 
 
-      {{#register-button class="btn btn-info btn-join navbar-btn btn-sm"}}
-        {{gettext "Join now"}}
-      {{/register-button}}
-    </div>
-    {{/if}}
+          </div>
+        </div>
 
 
-  </div><!-- /.container -->
+      </li>
+    </ul>
+  </li>
+  {{/if}}
+</ul>
+<!-- /.compact navbar -->
 </nav>
 </nav>

BIN
misago/emberapp/public/misago/img/misago_logo.png


BIN
misago/emberapp/public/misago/img/site-icon.png


BIN
misago/emberapp/public/misago/img/site-logo.png


+ 11 - 11
misago/emberapp/tests/acceptance/error-toast-test.js

@@ -5,7 +5,7 @@ import getToastMessage from '../helpers/toast-message';
 
 
 var application;
 var application;
 
 
-module('Acceptance: Application Error Handler', {
+module('Acceptance: Toasting Error Handler', {
   beforeEach: function() {
   beforeEach: function() {
     application = startApp();
     application = startApp();
   },
   },
@@ -21,13 +21,13 @@ test('some unhandled error occured', function(assert) {
   assert.expect(1);
   assert.expect(1);
 
 
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: '/api/auth/login/',
+    url: '/api/auth/',
     status: 500
     status: 500
   });
   });
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav button.btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
@@ -41,13 +41,13 @@ test('app went away', function(assert) {
   assert.expect(1);
   assert.expect(1);
 
 
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: '/api/auth/login/',
+    url: '/api/auth/',
     status: 0
     status: 0
   });
   });
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav button.btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
@@ -61,7 +61,7 @@ test('not found', function(assert) {
   assert.expect(1);
   assert.expect(1);
 
 
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: '/api/auth/login/',
+    url: '/api/auth/',
     status: 404,
     status: 404,
     responseText: {
     responseText: {
       'detail': 'Not found'
       'detail': 'Not found'
@@ -70,7 +70,7 @@ test('not found', function(assert) {
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav button.btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
@@ -84,7 +84,7 @@ test('permission denied', function(assert) {
   assert.expect(1);
   assert.expect(1);
 
 
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: '/api/auth/login/',
+    url: '/api/auth/',
     status: 403,
     status: 403,
     responseText: {
     responseText: {
       'detail': 'Permission denied'
       'detail': 'Permission denied'
@@ -93,7 +93,7 @@ test('permission denied', function(assert) {
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav button.btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
@@ -107,7 +107,7 @@ test('permission denied with reason', function(assert) {
   assert.expect(1);
   assert.expect(1);
 
 
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: '/api/auth/login/',
+    url: '/api/auth/',
     status: 403,
     status: 403,
     responseText: {
     responseText: {
       'detail': 'Lorem ipsum dolor met.'
       'detail': 'Lorem ipsum dolor met.'
@@ -116,7 +116,7 @@ test('permission denied with reason', function(assert) {
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav button.btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');

+ 13 - 13
misago/emberapp/tests/acceptance/login-test.js

@@ -27,7 +27,7 @@ test('login with empty credentials', function(assert) {
   assert.expect(1);
   assert.expect(1);
 
 
   visit('/');
   visit('/');
-  click('.guest-nav button.btn-login');
+  click('.navbar-guest-nav button.btn-default');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
 
 
   andThen(function() {
   andThen(function() {
@@ -39,13 +39,13 @@ test('backend errored', function(assert) {
   assert.expect(1);
   assert.expect(1);
 
 
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: "/api/auth/login/",
+    url: '/api/auth/',
     status: 500
     status: 500
   });
   });
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav .btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
@@ -60,7 +60,7 @@ test('login with invalid credentials', function(assert) {
 
 
   var message = 'Login or password is incorrect.';
   var message = 'Login or password is incorrect.';
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: "/api/auth/login/",
+    url: '/api/auth/',
     status: 400,
     status: 400,
     responseText: {
     responseText: {
       'detail': message,
       'detail': message,
@@ -70,7 +70,7 @@ test('login with invalid credentials', function(assert) {
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav .btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
@@ -85,7 +85,7 @@ test('login to user-activated account', function(assert) {
 
 
   var message = 'You have to activate your account before you will be able to sign in.';
   var message = 'You have to activate your account before you will be able to sign in.';
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: "/api/auth/login/",
+    url: '/api/auth/',
     status: 400,
     status: 400,
     responseText: {
     responseText: {
       'detail': message,
       'detail': message,
@@ -95,7 +95,7 @@ test('login to user-activated account', function(assert) {
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav .btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
@@ -110,7 +110,7 @@ test('login to admin-activated account', function(assert) {
 
 
   var message = 'Your account has to be activated by Administrator before you will be able to sign in.';
   var message = 'Your account has to be activated by Administrator before you will be able to sign in.';
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: "/api/auth/login/",
+    url: '/api/auth/',
     status: 400,
     status: 400,
     responseText: {
     responseText: {
       'detail': message,
       'detail': message,
@@ -120,7 +120,7 @@ test('login to admin-activated account', function(assert) {
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav .btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
@@ -134,7 +134,7 @@ test('login to banned account', function(assert) {
   assert.expect(3);
   assert.expect(3);
 
 
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: "/api/auth/login/",
+    url: '/api/auth/',
     status: 400,
     status: 400,
     responseText: {
     responseText: {
       'detail': {
       'detail': {
@@ -150,7 +150,7 @@ test('login to banned account', function(assert) {
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav .btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
@@ -170,7 +170,7 @@ test('login successfully', function(assert) {
   assert.expect(2);
   assert.expect(2);
 
 
   Ember.$.mockjax({
   Ember.$.mockjax({
-    url: "/api/auth/login/",
+    url: '/api/auth/',
     status: 200,
     status: 200,
     responseText: {
     responseText: {
       'username': 'SomeFake'
       'username': 'SomeFake'
@@ -179,7 +179,7 @@ test('login successfully', function(assert) {
 
 
   visit('/');
   visit('/');
 
 
-  click('.guest-nav .btn-login');
+  click('.navbar-guest-nav .btn-default');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:first-child input', 'SomeFake');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   fillIn('#appModal .form-group:last-child input', 'pass1234');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');

+ 8 - 8
misago/emberapp/tests/acceptance/registration-test.js

@@ -25,7 +25,7 @@ test('registration is closed', function(assert) {
   assert.expect(1);
   assert.expect(1);
 
 
   visit('/');
   visit('/');
-  click('.guest-nav button.btn-join');
+  click('.navbar-guest-nav button.btn-success');
 
 
   andThen(function() {
   andThen(function() {
     assert.equal(Ember.$.trim(find('.modal-register-closed .lead').text()), 'New registrations are currently not being accepted.');
     assert.equal(Ember.$.trim(find('.modal-register-closed .lead').text()), 'New registrations are currently not being accepted.');
@@ -36,7 +36,7 @@ test('register with empty credentials', function(assert) {
   assert.expect(1);
   assert.expect(1);
 
 
   visit('/');
   visit('/');
-  click('.guest-nav button.btn-join');
+  click('.navbar-guest-nav button.btn-success');
   click('#appModal .btn-primary');
   click('#appModal .btn-primary');
 
 
   andThen(function() {
   andThen(function() {
@@ -48,7 +48,7 @@ test('register with invalid credentials', function(assert) {
   assert.expect(1);
   assert.expect(1);
 
 
   visit('/');
   visit('/');
-  click('.guest-nav button.btn-join');
+  click('.navbar-guest-nav button.btn-success');
   fillIn('#appModal #id_username', 'a');
   fillIn('#appModal #id_username', 'a');
   fillIn('#appModal #id_password', 'b');
   fillIn('#appModal #id_password', 'b');
   fillIn('#appModal #id_email', 'c');
   fillIn('#appModal #id_email', 'c');
@@ -68,7 +68,7 @@ test('register with rejected credentials', function(assert) {
   });
   });
 
 
   visit('/');
   visit('/');
-  click('.guest-nav button.btn-join');
+  click('.navbar-guest-nav button.btn-success');
   fillIn('#appModal #id_username', 'Lorem');
   fillIn('#appModal #id_username', 'Lorem');
   fillIn('#appModal #id_password', 'ipsum123');
   fillIn('#appModal #id_password', 'ipsum123');
   fillIn('#appModal #id_email', 'lorem@ipsum.com');
   fillIn('#appModal #id_email', 'lorem@ipsum.com');
@@ -98,7 +98,7 @@ test('register banned', function(assert) {
   });
   });
 
 
   visit('/');
   visit('/');
-  click('.guest-nav button.btn-join');
+  click('.navbar-guest-nav button.btn-success');
   fillIn('#appModal #id_username', 'Lorem');
   fillIn('#appModal #id_username', 'Lorem');
   fillIn('#appModal #id_password', 'ipsum123');
   fillIn('#appModal #id_password', 'ipsum123');
   fillIn('#appModal #id_email', 'lorem@ipsum.com');
   fillIn('#appModal #id_email', 'lorem@ipsum.com');
@@ -129,7 +129,7 @@ test('register active user', function(assert) {
   });
   });
 
 
   visit('/');
   visit('/');
-  click('.guest-nav button.btn-join');
+  click('.navbar-guest-nav button.btn-success');
   fillIn('#appModal #id_username', 'Lorem');
   fillIn('#appModal #id_username', 'Lorem');
   fillIn('#appModal #id_password', 'ipsum123');
   fillIn('#appModal #id_password', 'ipsum123');
   fillIn('#appModal #id_email', 'lorem@ipsum.com');
   fillIn('#appModal #id_email', 'lorem@ipsum.com');
@@ -155,7 +155,7 @@ test('register admin-activated user', function(assert) {
   });
   });
 
 
   visit('/');
   visit('/');
-  click('.guest-nav button.btn-join');
+  click('.navbar-guest-nav button.btn-success');
   fillIn('#appModal #id_username', 'Lorem');
   fillIn('#appModal #id_username', 'Lorem');
   fillIn('#appModal #id_password', 'ipsum123');
   fillIn('#appModal #id_password', 'ipsum123');
   fillIn('#appModal #id_email', 'lorem@ipsum.com');
   fillIn('#appModal #id_email', 'lorem@ipsum.com');
@@ -181,7 +181,7 @@ test('register self-activated user', function(assert) {
   });
   });
 
 
   visit('/');
   visit('/');
-  click('.guest-nav button.btn-join');
+  click('.navbar-guest-nav button.btn-success');
   fillIn('#appModal #id_username', 'Lorem');
   fillIn('#appModal #id_username', 'Lorem');
   fillIn('#appModal #id_password', 'ipsum123');
   fillIn('#appModal #id_password', 'ipsum123');
   fillIn('#appModal #id_email', 'lorem@ipsum.com');
   fillIn('#appModal #id_email', 'lorem@ipsum.com');

+ 1 - 1
misago/emberapp/vendor/testutils/misago-preload-data.js

@@ -19,7 +19,7 @@ window.MisagoData = {
     "privacy_policy_title": "Polityka prywatno\u015bci",
     "privacy_policy_title": "Polityka prywatno\u015bci",
     "privacy_policy": true,
     "privacy_policy": true,
 
 
-    "loginApiUrl": "auth/login",
+    "loginApiUrl": "auth",
 
 
     "loginUrl": "/login/",
     "loginUrl": "/login/",
     "loginRedirectUrl": "/",
     "loginRedirectUrl": "/",

+ 1 - 0
misago/users/serializers/__init__.py

@@ -1,2 +1,3 @@
 from misago.users.serializers.ban import *
 from misago.users.serializers.ban import *
+from misago.users.serializers.rank import *
 from misago.users.serializers.user import *
 from misago.users.serializers.user import *

+ 19 - 0
misago/users/serializers/rank.py

@@ -0,0 +1,19 @@
+from rest_framework import serializers
+
+from misago.users.models import Rank
+
+
+__ALL__ = ['RankSerializer']
+
+
+class RankSerializer(serializers.ModelSerializer):
+    class Meta:
+        model = Rank
+        fields = (
+            'id',
+            'name',
+            'slug',
+            'description',
+            'title',
+            'css_class',
+            'is_tab')

+ 5 - 0
misago/users/serializers/user.py

@@ -4,12 +4,14 @@ from rest_framework import serializers
 
 
 from misago.acl import serialize_acl
 from misago.acl import serialize_acl
 
 
+from misago.users.serializers import RankSerializer
 
 
 __ALL__ = ['AuthenticatedUserSerializer', 'AnonymousUserSerializer']
 __ALL__ = ['AuthenticatedUserSerializer', 'AnonymousUserSerializer']
 
 
 
 
 class AuthenticatedUserSerializer(serializers.ModelSerializer):
 class AuthenticatedUserSerializer(serializers.ModelSerializer):
     acl = serializers.SerializerMethodField()
     acl = serializers.SerializerMethodField()
+    rank = RankSerializer(many=False, read_only=True)
 
 
     class Meta:
     class Meta:
         model = get_user_model()
         model = get_user_model()
@@ -21,6 +23,9 @@ class AuthenticatedUserSerializer(serializers.ModelSerializer):
             'joined_on',
             'joined_on',
             'is_hiding_presence',
             'is_hiding_presence',
             'title',
             'title',
+            'full_title',
+            'short_title',
+            'rank',
             'new_notifications',
             'new_notifications',
             'limits_private_thread_invites_to',
             'limits_private_thread_invites_to',
             'unread_private_threads',
             'unread_private_threads',