Browse Source

Merge branch 'support/apply-bootstrap4' into support/reactify-login-page

yusuketk 6 years ago
parent
commit
ea2402d89f
25 changed files with 336 additions and 286 deletions
  1. 13 3
      src/client/js/components/Admin/MarkdownSetting/PresentationForm.jsx
  2. 21 19
      src/client/js/components/Admin/Notification/GlobalNotificationList.jsx
  3. 73 61
      src/client/js/components/Admin/Notification/ManageGlobalNotification.jsx
  4. 1 1
      src/client/js/components/Admin/Notification/UserNotificationRow.jsx
  5. 1 1
      src/client/js/components/Admin/Notification/UserTriggerNotification.jsx
  6. 1 1
      src/client/js/components/Admin/Security/GitHubSecuritySetting.jsx
  7. 13 11
      src/client/js/components/Admin/Security/LdapAuthTest.jsx
  8. 1 1
      src/client/js/components/Admin/UserGroupDetail/UserGroupUserFormByInput.jsx
  9. 1 1
      src/client/js/components/Admin/UserManagement.jsx
  10. 1 1
      src/client/js/components/Admin/Users/UserMenu.jsx
  11. 1 1
      src/client/js/components/Navbar/PageCreator.jsx
  12. 2 2
      src/client/js/components/Navbar/RevisionAuthor.jsx
  13. 2 0
      src/client/js/services/AppContainer.js
  14. 1 1
      src/client/styles/scss/_editor-attachment.scss
  15. 6 6
      src/client/styles/scss/_layout.scss
  16. 1 0
      src/client/styles/scss/_on-edit.scss
  17. 145 140
      src/client/styles/scss/_override-bootstrap.scss
  18. 1 1
      src/client/styles/scss/_tag.scss
  19. 13 5
      src/client/styles/scss/_vendor.scss
  20. 1 1
      src/client/styles/scss/style-app.scss
  21. 5 4
      src/client/styles/scss/theme/_apply-colors.scss
  22. 5 12
      src/client/styles/scss/theme/_reboot-bootstrap-colors.scss
  23. 15 0
      src/client/styles/scss/theme/_reboot-toastr-colors.scss
  24. 1 2
      src/client/styles/scss/theme/default.scss
  25. 11 11
      src/server/views/modal/shortcuts.html

+ 13 - 3
src/client/js/components/Admin/MarkdownSetting/PresentationForm.jsx

@@ -42,7 +42,7 @@ class PresentationForm extends React.Component {
     return (
       <fieldset className="form-group col-12 my-2">
 
-        <label className="col-12 control-label font-weight-bold text-left mt-3">
+        <label className="col-8 offset-4 control-label font-weight-bold text-left mt-3">
           {t('admin:markdown_setting.presentation_options.page_break_setting')}
         </label>
 
@@ -60,7 +60,12 @@ class PresentationForm extends React.Component {
                 <p className="font-weight-bold">{ t('admin:markdown_setting.presentation_options.preset_one_separator') }</p>
                 <div className="mt-3">
                   { t('admin:markdown_setting.presentation_options.preset_one_separator_desc') }
-                  <pre><code>{ t('admin:markdown_setting.presentation_options.preset_one_separator_value') }</code></pre>
+                  <input
+                    className="form-control"
+                    type="text"
+                    value={t('admin:markdown_setting.presentation_options.preset_one_separator_value')}
+                    readOnly
+                  />
                 </div>
               </label>
             </div>
@@ -79,7 +84,12 @@ class PresentationForm extends React.Component {
                 <p className="font-weight-bold">{ t('admin:markdown_setting.presentation_options.preset_two_separator') }</p>
                 <div className="mt-3">
                   { t('admin:markdown_setting.presentation_options.preset_two_separator_desc') }
-                  <pre><code>{ t('admin:markdown_setting.presentation_options.preset_two_separator_value') }</code></pre>
+                  <input
+                    className="form-control"
+                    type="text"
+                    value={t('admin:markdown_setting.presentation_options.preset_two_separator_value')}
+                    readOnly
+                  />
                 </div>
               </label>
             </div>

+ 21 - 19
src/client/js/components/Admin/Notification/GlobalNotificationList.jsx

@@ -91,42 +91,44 @@ class GlobalNotificationList extends React.Component {
                 {notification.triggerPath}
               </td>
               <td>
-                {notification.triggerEvents.includes('pageCreate') && (
-                  <span className="badge badge-pill badge-success" data-toggle="tooltip" data-placement="top" title="Page Create">
+                <ul className="list-inline">
+                  {notification.triggerEvents.includes('pageCreate') && (
+                  <li className="list-inline-item badge badge-pill badge-success" data-toggle="tooltip" data-placement="top" title="Page Create">
                     <i className="icon-doc"></i> CREATE
-                  </span>
+                  </li>
                 )}
-                {notification.triggerEvents.includes('pageEdit') && (
-                  <span className="badge badge-pill badge-warning" data-toggle="tooltip" data-placement="top" title="Page Edit">
+                  {notification.triggerEvents.includes('pageEdit') && (
+                  <li className="list-inline-item badge badge-pill badge-warning" data-toggle="tooltip" data-placement="top" title="Page Edit">
                     <i className="icon-pencil"></i> EDIT
-                  </span>
+                  </li>
                 )}
-                {notification.triggerEvents.includes('pageMove') && (
-                  <span className="badge badge-pill badge-warning" data-toggle="tooltip" data-placement="top" title="Page Move">
+                  {notification.triggerEvents.includes('pageMove') && (
+                  <li className="list-inline-item badge badge-pill badge-warning" data-toggle="tooltip" data-placement="top" title="Page Move">
                     <i className="icon-action-redo"></i> MOVE
-                  </span>
+                  </li>
                 )}
-                {notification.triggerEvents.includes('pageDelete') && (
-                  <span className="badge badge-pill badge-danger" data-toggle="tooltip" data-placement="top" title="Page Delte">
+                  {notification.triggerEvents.includes('pageDelete') && (
+                  <li className="list-inline-item badge badge-pill badge-danger" data-toggle="tooltip" data-placement="top" title="Page Delte">
                     <i className="icon-fire"></i> DELETE
-                  </span>
+                  </li>
                 )}
-                {notification.triggerEvents.includes('pageLike') && (
-                  <span className="badge badge-pill badge-info" data-toggle="tooltip" data-placement="top" title="Page Like">
+                  {notification.triggerEvents.includes('pageLike') && (
+                  <li className="list-inline-item badge badge-pill badge-info" data-toggle="tooltip" data-placement="top" title="Page Like">
                     <i className="icon-like"></i> LIKE
-                  </span>
+                  </li>
                 )}
-                {notification.triggerEvents.includes('comment') && (
-                  <span className="badge badge-pill badge-light" data-toggle="tooltip" data-placement="top" title="New Comment">
+                  {notification.triggerEvents.includes('comment') && (
+                  <li className="list-inline-item badge badge-pill badge-light" data-toggle="tooltip" data-placement="top" title="New Comment">
                     <i className="icon-fw icon-bubble"></i> POST
-                  </span>
+                  </li>
                 )}
+                </ul>
               </td>
               <td>
                 {notification.__t === 'mail'
                   && <span data-toggle="tooltip" data-placement="top" title="Email"><i className="ti-email"></i> {notification.toEmail}</span>}
                 {notification.__t === 'slack'
-                  && <span data-toggle="tooltip" data-placement="top" title="Slack"><i className="fa fa-slack"></i> {notification.slackChannels}</span>}
+                  && <span data-toggle="tooltip" data-placement="top" title="Slack"><i className="fa fa-hashtag"></i> {notification.slackChannels}</span>}
               </td>
               <td className="td-abs-center">
                 <div className="dropdown">

+ 73 - 61
src/client/js/components/Admin/Notification/ManageGlobalNotification.jsx

@@ -193,7 +193,7 @@ class ManageGlobalNotification extends React.Component {
                 <>
                   <div className="input-group notify-to-option" id="slack-input">
                     <div className="input-group-prepend">
-                      <span className="input-group-text" id="slack-channel-addon"><i className="fa fa-slack" /></span>
+                      <span className="input-group-text" id="slack-channel-addon"><i className="fa fa-hashtag" /></span>
                     </div>
                     <input
                       className="form-control"
@@ -216,66 +216,78 @@ class ManageGlobalNotification extends React.Component {
           <div className="offset-1 col-sm-5">
             <div className="form-group">
               <h3>{t('notification_setting.trigger_events')}</h3>
-              <TriggerEventCheckBox
-                checkbox="success"
-                event="pageCreate"
-                checked={this.state.triggerEvents.has('pageCreate')}
-                onChange={() => this.onChangeTriggerEvents('pageCreate')}
-              >
-                <span className="badge badge-pill badge-success">
-                  <i className="icon-doc"></i> CREATE
-                </span>
-              </TriggerEventCheckBox>
-              <TriggerEventCheckBox
-                checkbox="warning"
-                event="pageEdit"
-                checked={this.state.triggerEvents.has('pageEdit')}
-                onChange={() => this.onChangeTriggerEvents('pageEdit')}
-              >
-                <span className="badge badge-pill badge-warning">
-                  <i className="icon-pencil"></i>EDIT
-                </span>
-              </TriggerEventCheckBox>
-              <TriggerEventCheckBox
-                checkbox="warning"
-                event="pageMove"
-                checked={this.state.triggerEvents.has('pageMove')}
-                onChange={() => this.onChangeTriggerEvents('pageMove')}
-              >
-                <span className="badge badge-pill badge-warning">
-                  <i className="icon-action-redo"></i>MOVE
-                </span>
-              </TriggerEventCheckBox>
-              <TriggerEventCheckBox
-                checkbox="danger"
-                event="pageDelete"
-                checked={this.state.triggerEvents.has('pageDelete')}
-                onChange={() => this.onChangeTriggerEvents('pageDelete')}
-              >
-                <span className="badge badge-pill badge-danger">
-                  <i className="icon-fire"></i>DELETE
-                </span>
-              </TriggerEventCheckBox>
-              <TriggerEventCheckBox
-                checkbox="info"
-                event="pageLike"
-                checked={this.state.triggerEvents.has('pageLike')}
-                onChange={() => this.onChangeTriggerEvents('pageLike')}
-              >
-                <span className="badge badge-pill badge-info">
-                  <i className="icon-like"></i>LIKE
-                </span>
-              </TriggerEventCheckBox>
-              <TriggerEventCheckBox
-                checkbox="secondary"
-                event="comment"
-                checked={this.state.triggerEvents.has('comment')}
-                onChange={() => this.onChangeTriggerEvents('comment')}
-              >
-                <span className="badge badge-pill badge-light">
-                  <i className="icon-bubble"></i>POST
-                </span>
-              </TriggerEventCheckBox>
+              <div className="my-1">
+                <TriggerEventCheckBox
+                  checkbox="success"
+                  event="pageCreate"
+                  checked={this.state.triggerEvents.has('pageCreate')}
+                  onChange={() => this.onChangeTriggerEvents('pageCreate')}
+                >
+                  <span className="badge badge-pill badge-success">
+                    <i className="icon-doc mr-1" /> CREATE
+                  </span>
+                </TriggerEventCheckBox>
+              </div>
+              <div className="my-1">
+                <TriggerEventCheckBox
+                  checkbox="warning"
+                  event="pageEdit"
+                  checked={this.state.triggerEvents.has('pageEdit')}
+                  onChange={() => this.onChangeTriggerEvents('pageEdit')}
+                >
+                  <span className="badge badge-pill badge-warning">
+                    <i className="icon-pencil mr-1" />EDIT
+                  </span>
+                </TriggerEventCheckBox>
+              </div>
+              <div className="my-1">
+                <TriggerEventCheckBox
+                  checkbox="warning"
+                  event="pageMove"
+                  checked={this.state.triggerEvents.has('pageMove')}
+                  onChange={() => this.onChangeTriggerEvents('pageMove')}
+                >
+                  <span className="badge badge-pill badge-warning">
+                    <i className="icon-action-redo mr-1" />MOVE
+                  </span>
+                </TriggerEventCheckBox>
+              </div>
+              <div className="my-1">
+                <TriggerEventCheckBox
+                  checkbox="danger"
+                  event="pageDelete"
+                  checked={this.state.triggerEvents.has('pageDelete')}
+                  onChange={() => this.onChangeTriggerEvents('pageDelete')}
+                >
+                  <span className="badge badge-pill badge-danger">
+                    <i className="icon-fire mr-1" />DELETE
+                  </span>
+                </TriggerEventCheckBox>
+              </div>
+              <div className="my-1">
+                <TriggerEventCheckBox
+                  checkbox="info"
+                  event="pageLike"
+                  checked={this.state.triggerEvents.has('pageLike')}
+                  onChange={() => this.onChangeTriggerEvents('pageLike')}
+                >
+                  <span className="badge badge-pill badge-info">
+                    <i className="icon-like mr-1" />LIKE
+                  </span>
+                </TriggerEventCheckBox>
+              </div>
+              <div className="my-1">
+                <TriggerEventCheckBox
+                  checkbox="secondary"
+                  event="comment"
+                  checked={this.state.triggerEvents.has('comment')}
+                  onChange={() => this.onChangeTriggerEvents('comment')}
+                >
+                  <span className="badge badge-pill badge-secondary">
+                    <i className="icon-bubble mr-1" />POST
+                  </span>
+                </TriggerEventCheckBox>
+              </div>
 
             </div>
           </div>

+ 1 - 1
src/client/js/components/Admin/Notification/UserNotificationRow.jsx

@@ -19,7 +19,7 @@ class UserNotificationRow extends React.PureComponent {
             {notification.pathPattern}
           </td>
           <td className="px-4">
-            <span data-toggle="tooltip" data-placement="top" title="Slack"><i className="fa fa-slack"></i> {notification.channel}</span>
+            <span data-toggle="tooltip" data-placement="top" title="Slack"><i className="fa fa-hashtag"></i> {notification.channel}</span>
           </td>
           <td>
             <button type="submit" className="btn btn-outline-danger" onClick={() => { this.props.onClickDeleteBtn(notification._id) }}>{t('Delete')}</button>

+ 1 - 1
src/client/js/components/Admin/Notification/UserTriggerNotification.jsx

@@ -112,7 +112,7 @@ class UserTriggerNotification extends React.Component {
               <td>
                 <div className="input-group notify-to-option" id="slack-input">
                   <div className="input-group-prepend">
-                    <span className="input-group-text"><i className="fa fa-slack" /></span>
+                    <span className="input-group-text"><i className="fa fa-hashtag" /></span>
                   </div>
                   <input
                     className="form-control form-inline"

+ 1 - 1
src/client/js/components/Admin/Security/GitHubSecuritySetting.jsx

@@ -83,7 +83,7 @@ class GitHubSecurityManagement extends React.Component {
               </label>
             </div>
             {(!adminGeneralSecurityContainer.state.setupStrategies.includes('github') && isGitHubEnabled)
-              && <div className="badg badge-warning">{t('security_setting.setup_is_not_yet_complete')}</div>}
+              && <div className="badge badge-warning">{t('security_setting.setup_is_not_yet_complete')}</div>}
           </div>
         </div>
 

+ 13 - 11
src/client/js/components/Admin/Security/LdapAuthTest.jsx

@@ -88,9 +88,9 @@ class LdapAuthTest extends React.Component {
       <React.Fragment>
         {this.state.successMessage != null && <div className="alert alert-success">{this.state.successMessage}</div>}
         {this.state.errorMessage != null && <div className="alert alert-warning">{this.state.errorMessage}</div>}
-        <div className="row p-3">
-          <label htmlFor="username" className="col-xs-3 text-right">{t('username')}</label>
-          <div className="col-xs-6">
+        <div className="form-group row">
+          <label htmlFor="username" className="col-3 col-form-label">{t('username')}</label>
+          <div className="col-6">
             <input
               className="form-control"
               name="username"
@@ -99,9 +99,9 @@ class LdapAuthTest extends React.Component {
             />
           </div>
         </div>
-        <div className="row p-3">
-          <label htmlFor="password" className="col-xs-3 text-right">{t('Password')}</label>
-          <div className="col-xs-6">
+        <div className="form-group row">
+          <label htmlFor="password" className="col-3 col-form-label">{t('Password')}</label>
+          <div className="col-6">
             <input
               className="form-control"
               type="password"
@@ -111,13 +111,15 @@ class LdapAuthTest extends React.Component {
             />
           </div>
         </div>
-        <div>
-          <h5>Logs</h5>
-          <textarea id="taLogs" className="col-xs-12" rows="4" value={this.state.logs} readOnly />
-        </div>
 
-        <button type="button" className="btn btn-outline-secondary mt-3 col-xs-offset-5 col-xs-2" onClick={this.testLdapCredentials}>Test</button>
+        <div className="form-group">
+          <label><h5>Logs</h5></label>
+          <textarea id="taLogs" className="col" rows="4" value={this.state.logs} readOnly />
+        </div>
 
+        <div>
+          <button type="button" className="btn btn-outline-secondary offset-5 col-2" onClick={this.testLdapCredentials}>Test</button>
+        </div>
       </React.Fragment>
 
     );

+ 1 - 1
src/client/js/components/Admin/UserGroupDetail/UserGroupUserFormByInput.jsx

@@ -140,7 +140,7 @@ class UserGroupUserFormByInput extends React.Component {
         <div className="col-2 pl-0">
           <button
             type="button"
-            className="btn btn-sm btn-success"
+            className="btn btn-success"
             disabled={!this.validateForm()}
             onClick={this.addUserBySubmit}
           >

+ 1 - 1
src/client/js/components/Admin/UserManagement.jsx

@@ -95,7 +95,7 @@ class UserManagement extends React.Component {
     const { t, adminUsersContainer } = this.props;
 
     const pager = (
-      <div className="pull-right">
+      <div className="pull-right my-3">
         <PaginationWrapper
           activePage={adminUsersContainer.state.activePage}
           changePage={this.handlePage}

+ 1 - 1
src/client/js/components/Admin/Users/UserMenu.jsx

@@ -36,7 +36,7 @@ class UserMenu extends React.Component {
         <li className="dropdown-divider"></li>
         <li className="dropdown-header">{t('admin:user_management.user_table.edit_menu')}</li>
         <li>
-          <a className="dropdown-item" href="" onClick={this.onPasswordResetClicked}>
+          <a className="dropdown-item" href="#" onClick={this.onPasswordResetClicked}>
             <i className="icon-fw icon-key"></i>{ t('admin:user_management.reset_password') }
           </a>
         </li>

+ 1 - 1
src/client/js/components/Navbar/PageCreator.jsx

@@ -7,7 +7,7 @@ import { userPageRoot } from '../../../../lib/util/path-utils';
 const PageCreator = (props) => {
   const { creator, createdAt, isCompactMode } = props;
   const creatInfo = isCompactMode
-    ? (<div>Created in <span className="text-muted">{createdAt}</span></div>)
+    ? (<div>Created at <span className="text-muted">{createdAt}</span></div>)
     : (<div><div>Created by <a href={userPageRoot(creator)}>{creator.name}</a></div><div className="text-muted">{createdAt}</div></div>);
   const pictureSize = isCompactMode ? 'xs' : 'sm';
 

+ 2 - 2
src/client/js/components/Navbar/RevisionAuthor.jsx

@@ -7,8 +7,8 @@ import { userPageRoot } from '../../../../lib/util/path-utils';
 const RevisionAuthor = (props) => {
   const { revisionAuthor, updatedAt, isCompactMode } = props;
   const updateInfo = isCompactMode
-    ? (<div>Updated in <span className="text-muted">{updatedAt}</span></div>)
-    : (<div><div>Updated in  <a href={userPageRoot(revisionAuthor)}>{revisionAuthor.name}</a></div><div className="text-muted">{updatedAt}</div></div>);
+    ? (<div>Updated at <span className="text-muted">{updatedAt}</span></div>)
+    : (<div><div>Updated by  <a href={userPageRoot(revisionAuthor)}>{revisionAuthor.name}</a></div><div className="text-muted">{updatedAt}</div></div>);
   const pictureSize = isCompactMode ? 'xs' : 'sm';
 
   return (

+ 2 - 0
src/client/js/services/AppContainer.js

@@ -374,10 +374,12 @@ export default class AppContainer extends Container {
 
     // switch to dark mode
     if (isDarkMode) {
+      document.documentElement.removeAttribute('light');
       document.documentElement.setAttribute('dark', 'true');
     }
     // switch to light mode
     else {
+      document.documentElement.setAttribute('light', 'true');
       document.documentElement.removeAttribute('dark');
     }
   }

+ 1 - 1
src/client/styles/scss/_editor-attachment.scss

@@ -100,7 +100,7 @@
     /* end of.dropzone */
   }
 
-  .btn-open-dropzone {
+  .btn.btn-open-dropzone {
     z-index: 2;
     padding-top: 3px;
     padding-bottom: 3px;

+ 6 - 6
src/client/styles/scss/_layout.scss

@@ -48,7 +48,7 @@
   border-bottom: 1px solid $grw-line-gray;
 }
 
-header {
+header#page-header {
   padding-top: 0.5rem;
   padding-bottom: 0.5rem;
 
@@ -90,11 +90,11 @@ header {
   }
 }
 
-  .revision-toc {
-    // to get on the Attachment row
-    z-index: 1;
-    overflow: hidden;
-    font-size: 0.9em;
+.revision-toc {
+  // to get on the Attachment row
+  z-index: 1;
+  overflow: hidden;
+  font-size: 0.9em;
 
   .revision-toc-content {
     padding: 10px;

+ 1 - 0
src/client/styles/scss/_on-edit.scss

@@ -25,6 +25,7 @@ body.on-edit {
   }
 
   // hide unnecessary elements
+  header,
   .grw-subnav,
   .row.row-alerts,
   .row.page-list,

+ 145 - 140
src/client/styles/scss/_override-bootstrap.scss

@@ -1,183 +1,188 @@
-* {
-  outline: none !important;
-}
-
+// increase specificity with ':root' for GROWI theming
 :root {
   font-size: $font-size-root;
   > body {
     font-family: $font-family-sans-serif;
   }
-}
 
-h1 {
-  font-size: 36px;
-  line-height: 48px;
-}
+  * {
+    outline: none !important;
+  }
 
-h2 {
-  font-size: 24px;
-  line-height: 36px;
-}
+  h1 {
+    font-size: 36px;
+    line-height: 48px;
+  }
 
-h3 {
-  font-size: 21px;
-  line-height: 30px;
-}
+  h2 {
+    font-size: 24px;
+    line-height: 36px;
+  }
 
-h4 {
-  font-size: 18px;
-  line-height: 22px;
-}
+  h3 {
+    font-size: 21px;
+    line-height: 30px;
+  }
 
-h5 {
-  font-size: 16px;
-  line-height: 18px;
-}
+  h4 {
+    font-size: 18px;
+    line-height: 22px;
+  }
 
-h6 {
-  font-size: 12px;
-  line-height: 14px;
-}
+  h5 {
+    font-size: 16px;
+    line-height: 18px;
+  }
 
-.small {
-  font-size: 65%;
-  line-height: 10px;
-}
+  h6 {
+    font-size: 12px;
+    line-height: 14px;
+  }
 
-// Navs
-.nav-tabs {
-  .nav-item {
-    margin-right: 0.15rem;
-    a.active {
-      cursor: default;
-    }
+  .small {
+    font-size: 65%;
+    line-height: 10px;
   }
-}
 
-// card (substitute panel of bootstrap3)
-.card {
-  margin-bottom: 20px;
-  border-radius: $card-border-radius;
-}
+  // Navs
+  .nav-tabs {
+    .nav-item {
+      margin-right: 0.15rem;
+      a.active {
+        cursor: default;
+      }
+    }
+  }
 
-.card-header {
-  font-weight: 700;
-  text-transform: none;
-  border-radius: $card-border-radius;
-}
+  // card (substitute panel of bootstrap3)
+  .card {
+    margin-bottom: 20px;
+    border-radius: $card-border-radius;
+  }
 
-.card-header:first-child {
-  border-radius: $card-border-radius;
-}
+  .card-header {
+    font-weight: 700;
+    text-transform: none;
+    border-radius: $card-border-radius;
+  }
 
-// Well (substitute Well of bootstrap3)
-.card.well {
-  min-height: 20px;
-  padding: $card-spacer-y $card-spacer-x;
-  border-radius: 3px;
-}
+  .card-header:first-child {
+    border-radius: $card-border-radius;
+  }
 
-// Dropdowns
-.dropdown {
-  .dropdown-toggle.btn.disabled {
-    cursor: not-allowed;
+  // Well (substitute Well of bootstrap3)
+  .card.well {
+    min-height: 20px;
+    padding: $card-spacer-y $card-spacer-x;
+    border-radius: 3px;
   }
 
-  // hide caret
-  .dropdown-toggle.dropdown-toggle-no-caret::after {
-    content: none;
+  // Dropdowns
+  .dropdown {
+    .dropdown-toggle.btn.disabled {
+      cursor: not-allowed;
+    }
+
+    // hide caret
+    .dropdown-toggle.dropdown-toggle-no-caret::after {
+      content: none;
+    }
   }
-}
 
-// agile-admin style
-.dropdown-menu {
-  padding-bottom: 8px;
-  margin-top: 0px;
-  border: 1px solid $border;
-  border-radius: $radius;
-  box-shadow: 0 3px 12px rgba(0, 0, 0, 0.05) !important;
-}
+  // agile-admin style
+  .dropdown-menu {
+    padding-bottom: 8px;
+    margin-top: 0px;
+    border: 1px solid $border;
+    border-radius: $radius;
+    box-shadow: 0 3px 12px rgba(0, 0, 0, 0.05) !important;
+  }
 
-.dropdown-menu > li > a {
-  width: 100%;
-  padding: 9px 20px;
-}
+  .dropdown-menu > li > a {
+    width: 100%;
+    padding: 9px 20px;
+  }
 
-.dropdown-menu > li > a:focus,
-.dropdown-menu > li > a:hover {
-  background: $extralight;
-}
+  .dropdown-menu > li > a:focus,
+  .dropdown-menu > li > a:hover {
+    background: $extralight;
+  }
 
-// btn-light (substitute for btn-default of bootstrap3)  (agile-admin style)
-.btn-light,
-.btn-light.disabled {
-  color: $bodytext;
-  $this-color: $btn-default-bgcolor;
-  background: $this-color;
-  border: 1px solid $this-color;
-
-  &:hover,
-  &:focus,
-  &.focus {
+  // btn-light (substitute for btn-default of bootstrap3)  (agile-admin style)
+  .btn-light,
+  .btn-light.disabled {
     color: $bodytext;
+    $this-color: $btn-default-bgcolor;
     background: $this-color;
     border: 1px solid $this-color;
-    opacity: 0.8;
-  }
 
-  &:active &.active {
-    box-shadow: none;
+    &:hover,
+    &:focus,
+    &.focus {
+      color: $bodytext;
+      background: $this-color;
+      border: 1px solid $this-color;
+      opacity: 0.8;
+    }
+
+    &:active &.active {
+      box-shadow: none;
+    }
   }
-}
 
-.btn-light.btn-outline {
-  background-color: transparent;
+  .btn-light.btn-outline {
+    background-color: transparent;
 
-  &:hover,
-  &:focus,
-  &.focus {
-    background: $btn-default-bgcolor;
+    &:hover,
+    &:focus,
+    &.focus {
+      background: $btn-default-bgcolor;
+    }
   }
-}
 
-//Modals
-.modal-content {
-  box-shadow: 0 0.3rem 1rem rgba(0, 0, 0, 0.1);
-}
+  //Modals
+  .modal-content {
+    box-shadow: 0 0.3rem 1rem rgba(0, 0, 0, 0.1);
+  }
 
-.modal-header {
-  border-bottom: 1px solid #e5e5e5;
-}
+  .modal-header {
+    border-bottom: 1px solid #e5e5e5;
+  }
 
-.modal-footer {
-  border-top: 1px solid #e5e5e5;
-}
+  .modal-footer {
+    border-top: 1px solid #e5e5e5;
+  }
 
-// col-form-label (substitute for control-label of bootstrap3)
-.col-form-label {
-  text-align: right;
-}
+  // col-form-label (substitute for control-label of bootstrap3)
+  .col-form-label {
+    text-align: right;
+  }
 
-// label
-label {
-  font-weight: 700;
-}
+  // label
+  label {
+    font-weight: 700;
+  }
 
-// disabled button (reproduction from bootstrap3.)
-// see https://cccabinet.jpn.org/bootstrap4/components/buttons#disabled-state
-.btn.disabled,
-.btn[disabled],
-fieldset[disabled] .btn {
-  cursor: not-allowed;
-}
+  // disabled button (reproduction from bootstrap3.)
+  // see https://cccabinet.jpn.org/bootstrap4/components/buttons#disabled-state
+  .btn.disabled,
+  .btn[disabled],
+  fieldset[disabled] .btn {
+    cursor: not-allowed;
+  }
 
-// progress bar
-.progress {
-  margin-bottom: 18px;
-  overflow: hidden;
-}
+  // progress bar
+  .progress {
+    margin-bottom: 18px;
+    overflow: hidden;
+  }
 
-// badge
-.badge {
-  letter-spacing: 0.05em;
+  // badge
+  .badge {
+    letter-spacing: 0.05em;
+    &.badge-warning {
+      // badge-warning text is white color in bootstrap3
+      color: white;
+    }
+  }
 }

+ 1 - 1
src/client/styles/scss/_tag.scss

@@ -8,7 +8,7 @@
     margin-left: 5px;
   }
 
-  .btn-edit-tags,
+  .btn.btn-edit-tags,
   .tag-icon {
     font-size: 10px;
   }

+ 13 - 5
src/client/styles/scss/_vendor.scss

@@ -1,12 +1,20 @@
-// import bootstrap
-@import '~bootstrap/scss/bootstrap';
+// import bootstrap configurations
+@import '~bootstrap/scss/functions';
+@import '~bootstrap/scss/variables';
+@import '~bootstrap/scss/mixins';
+@import '~bootstrap/scss/utilities';
+
+// increase specificity with ':root' for GROWI theming
+:root {
+  // import bootstrap
+  @import '~bootstrap/scss/bootstrap';
+  // import toastr styles
+  @import '~toastr/build/toastr';
+}
 
 // import react-bootstrap-typeahead
 @import '~react-bootstrap-typeahead/css/Typeahead';
 
-// import toastr styles
-@import '~toastr/build/toastr';
-
 // import CodeMirror styles
 @import '~codemirror/lib/codemirror.css';
 @import '~codemirror/theme/elegant.css';

+ 1 - 1
src/client/styles/scss/style-app.scss

@@ -20,7 +20,7 @@
 @import 'atoms/spinners';
 @import 'atoms/custom_control';
 
-// crowi component
+// growi component
 @import 'admin';
 @import 'attachments';
 @import 'comment';

+ 5 - 4
src/client/styles/scss/theme/_apply-colors.scss

@@ -8,8 +8,12 @@ $body-color: $color-global;
 $link-color: $color-link;
 $link-hover-color: $color-link-hover;
 
+@import '~bootstrap/scss/functions';
+@import '~bootstrap/scss/variables';
+@import '~bootstrap/scss/mixins';
 @import 'reboot-bootstrap-colors';
 @import 'reboot-bootstrap-theme-colors';
+@import 'reboot-toastr-colors';
 
 // Link buttons
 .btn-link {
@@ -28,9 +32,6 @@ $link-hover-color: $color-link-hover;
     color: $color-dropdown-link-active;
     background-color: $bgcolor-dropdown-link-active;
   }
-  &:hover:not(.active) {
-    color: $color-dropdown-link-hover;
-  }
 }
 
 // Form
@@ -317,4 +318,4 @@ body.on-edit {
       }
     }
   }
-}
+}

+ 5 - 12
src/client/styles/scss/theme/_reboot-bootstrap-colors.scss

@@ -1,6 +1,3 @@
-@import '~bootstrap/scss/functions';
-@import '~bootstrap/scss/variables';
-@import '~bootstrap/scss/mixins';
 //
 //
 // Apply partially
@@ -190,17 +187,13 @@ body {
 //
 
 a {
-  :not(.badge) {
-    color: $link-color;
-    // text-decoration: $link-decoration;
-    background-color: transparent; // Remove the gray background on active links in IE 10.
-  }
+  color: $link-color;
+  text-decoration: $link-decoration;
+  background-color: transparent; // Remove the gray background on active links in IE 10.
 
   @include hover() {
-    &:not(.list-group-item) {
-      color: $link-hover-color;
-      // text-decoration: $link-hover-decoration;
-    }
+    color: $link-hover-color;
+    text-decoration: $link-hover-decoration;
   }
 }
 

+ 15 - 0
src/client/styles/scss/theme/_reboot-toastr-colors.scss

@@ -0,0 +1,15 @@
+.toast-success {
+  background-color: $success;
+}
+
+.toast-error {
+  background-color: $danger;
+}
+
+.toast-info {
+  background-color: $info;
+}
+
+.toast-warning {
+  background-color: $warning;
+}

+ 1 - 2
src/client/styles/scss/theme/default.scss

@@ -15,7 +15,7 @@
 
 //== Light Mode
 //
-html:not([dark]) {
+html[light] {
   $primary: #112744;
 
   // Background colors
@@ -43,7 +43,6 @@ html:not([dark]) {
   // Dropdown colors
   $bgcolor-dropdown-link-active: $growi-blue;
   $color-dropdown-link-active: $color-reversal;
-  $color-dropdown-link-hover: $color-global;
 
   @import 'apply-colors';
   @import 'apply-colors-light';

+ 11 - 11
src/server/views/modal/shortcuts.html

@@ -1,16 +1,16 @@
 <div class="modal" id="shortcuts-modal" tabindex="-1">
-  <div class="modal-dialog">
+  <div class="modal-dialog modal-lg">
     <div class="modal-content">
 
       <div class="modal-header">
-        <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
         <div class="modal-title">{{ t('Shortcuts') }}</div>
+        <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
       </div>
 
       <div class="modal-body">
 
         <div class="row">
-          <div class="col-sm-6">
+          <div class="col-md-6">
             <h3><strong>{{ t('modal_shortcuts.global.title') }}</strong></h3>
 
             <table class="table">
@@ -38,9 +38,9 @@
                 </td>
               </tr>
             </table>
-          </div><!-- /.col-sm-6 -->
+          </div><!-- /.col-md-6 -->
 
-          <div class="col-sm-6">
+          <div class="col-md-6">
             <h3><strong>{{ t('modal_shortcuts.editor.title') }}</strong></h3>
 
             <table class="table">
@@ -50,7 +50,7 @@
               </tr>
               <tr>
                 <th>{{ t('modal_shortcuts.editor.Outdent') }}:</th>
-                <td><span class="key key-long">Shift</span> + <span class="key key-longer">Tab</span></td>
+                <td class="text-nowrap"><span class="key key-long">Shift</span> + <span class="key key-longer">Tab</span></td>
               </tr>
               <tr>
                 <th>{{ t('modal_shortcuts.editor.Save Page') }}:</th>
@@ -61,16 +61,16 @@
                 <td><span class="key cmd-key"></span> + <span class="key">D</span></td>
               </tr>
             </table>
-          </div><!-- /.col-sm-6 -->
+          </div><!-- /.col-md-6 -->
 
         </div><!-- /.row -->
 
         <div class="row">
-          <div class="col-sm-6">
+          <div class="col-md-6">
             <h3><strong></strong></h3>
-          </div><!-- /.col-sm-6 -->
+          </div><!-- /.col-md-6 -->
 
-          <div class="col-sm-6">
+          <div class="col-md-6">
             <h3><strong>{{ t('modal_shortcuts.commentform.title') }}</strong></h3>
 
             <table class="table">
@@ -83,7 +83,7 @@
                 <td><span class="key cmd-key"></span> + <span class="key">D</span></td>
               </tr>
             </table>
-          </div><!-- /.col-sm-6 -->
+          </div><!-- /.col-md-6 -->
 
         </div><!-- /.row -->