FEATURE: Add user preference for title counter mode (#7364)

FEATURE: Add user preference for title counter mode (#7364)

diff --git a/app/assets/javascripts/discourse.js.es6 b/app/assets/javascripts/discourse.js.es6
index 6e24d1e..ef6bbe5 100644
--- a/app/assets/javascripts/discourse.js.es6
+++ b/app/assets/javascripts/discourse.js.es6
@@ -51,9 +51,11 @@ const Discourse = Ember.Application.extend({
       $("title").text(title);
     }
 
-    var displayCount = Discourse.User.current()
-      ? this.get("notificationCount")
-      : this.get("contextCount");
+    var displayCount =
+      Discourse.User.current() &&
+      Discourse.User.currentProp("title_count_mode") === "notifications"
+        ? this.get("notificationCount")
+        : this.get("contextCount");
 
     if (displayCount > 0 && !Discourse.User.currentProp("dynamic_favicon")) {
       title = `(${displayCount}) ${title}`;
diff --git a/app/assets/javascripts/discourse/controllers/preferences/interface.js.es6 b/app/assets/javascripts/discourse/controllers/preferences/interface.js.es6
index 3b9d6e6..cba47fa 100644
--- a/app/assets/javascripts/discourse/controllers/preferences/interface.js.es6
+++ b/app/assets/javascripts/discourse/controllers/preferences/interface.js.es6
@@ -21,6 +21,7 @@ const USER_HOMES = {
 };
 
 const TEXT_SIZES = ["smaller", "normal", "larger", "largest"];
+const TITLE_COUNT_MODES = ["notifications", "contextual"];
 
 export default Ember.Controller.extend(PreferencesTabController, {
   @computed("makeThemeDefault")
@@ -35,7 +36,8 @@ export default Ember.Controller.extend(PreferencesTabController, {
       "allow_private_messages",
       "homepage_id",
       "hide_profile_and_presence",
-      "text_size"
+      "text_size",
+      "title_count_mode"
     ];
 
     if (makeDefault) {
@@ -69,6 +71,13 @@ export default Ember.Controller.extend(PreferencesTabController, {
     });
   },
 
+  @computed
+  titleCountModes() {
+    return TITLE_COUNT_MODES.map(value => {
+      return { name: I18n.t(`user.title_count_mode.${value}`), value };
+    });
+  },
+
   userSelectableThemes: function() {
     return listThemes(this.site);
   }.property(),
diff --git a/app/assets/javascripts/discourse/models/user.js.es6 b/app/assets/javascripts/discourse/models/user.js.es6
index 55a5801..f29a4e1 100644
--- a/app/assets/javascripts/discourse/models/user.js.es6
+++ b/app/assets/javascripts/discourse/models/user.js.es6
@@ -286,7 +286,8 @@ const User = RestModel.extend({
       "allow_private_messages",
       "homepage_id",
       "hide_profile_and_presence",
-      "text_size"
+      "text_size",
+      "title_count_mode"
     ];
 
     if (fields) {
diff --git a/app/assets/javascripts/discourse/templates/preferences/interface.hbs b/app/assets/javascripts/discourse/templates/preferences/interface.hbs
index a74f42b..6323af8 100644
--- a/app/assets/javascripts/discourse/templates/preferences/interface.hbs
+++ b/app/assets/javascripts/discourse/templates/preferences/interface.hbs
@@ -58,6 +58,13 @@
   {{#if isiPad}}
     {{preference-checkbox labelKey="user.enable_physical_keyboard" checked=disableSafariHacks}}
   {{/if}}
+  <div class='controls controls-dropdown'>
+    <label for="user-email-level">{{i18n 'user.title_count_mode.title'}}</label>
+    {{combo-box valueAttribute="value"
+                content=titleCountModes
+                value=model.user_option.title_count_mode
+                id="user-title-count-mode"}}
+  </div>
 </div>
 
 {{plugin-outlet name="user-preferences-interface" args=(hash model=model save=(action "save"))}}
diff --git a/app/models/user_option.rb b/app/models/user_option.rb
index 2feaba0..d75149b 100644
--- a/app/models/user_option.rb
+++ b/app/models/user_option.rb
@@ -29,6 +29,10 @@ class UserOption < ActiveRecord::Base
     @text_sizes ||= Enum.new(normal: 0, larger: 1, largest: 2, smaller: 3)
   end
 
+  def self.title_count_modes
+    @title_count_modes ||= Enum.new(notifications: 0, contextual: 1)
+  end
+
   def self.email_level_types
     @email_level_type ||= Enum.new(always: 0, only_when_away: 1, never: 2)
   end
@@ -68,6 +72,8 @@ class UserOption < ActiveRecord::Base
 
     self.text_size = SiteSetting.default_text_size
 
+    self.title_count_mode = SiteSetting.default_title_count_mode
+
     true
   end
 
@@ -164,6 +170,14 @@ class UserOption < ActiveRecord::Base
     self.text_size_key = UserOption.text_sizes[value.to_sym]
   end
 
+  def title_count_mode
+    UserOption.title_count_modes[title_count_mode_key]
+  end
+
+  def title_count_mode=(value)
+    self.title_count_mode_key = UserOption.title_count_modes[value.to_sym]
+  end
+
   private
 
   def update_tracked_topics
diff --git a/app/serializers/current_user_serializer.rb b/app/serializers/current_user_serializer.rb
index 7e6ddb0..2894b69 100644
--- a/app/serializers/current_user_serializer.rb
+++ b/app/serializers/current_user_serializer.rb
@@ -43,7 +43,8 @@ class CurrentUserSerializer < BasicUserSerializer
              :hide_profile_and_presence,
              :groups,
              :second_factor_enabled,
-             :ignored_users
+             :ignored_users,
+             :title_count_mode
 
   def groups
     object.visible_groups.pluck(:id, :name).map { |id, name| { id: id, name: name.downcase } }
@@ -89,6 +90,10 @@ class CurrentUserSerializer < BasicUserSerializer
     object.user_option.dynamic_favicon
   end
 
+  def title_count_mode
+    object.user_option.title_count_mode
+  end
+
   def automatically_unpin_topics
     object.user_option.automatically_unpin_topics
   end
diff --git a/app/serializers/user_option_serializer.rb b/app/serializers/user_option_serializer.rb
index 70b51e1..1ec5f4d 100644
--- a/app/serializers/user_option_serializer.rb
+++ b/app/serializers/user_option_serializer.rb
@@ -24,7 +24,8 @@ class UserOptionSerializer < ApplicationSerializer
              :homepage_id,
              :hide_profile_and_presence,
              :text_size,
-             :text_size_seq
+             :text_size_seq,
+             :title_count_mode
 
   def auto_track_topics_after_msecs
     object.auto_track_topics_after_msecs || SiteSetting.default_other_auto_track_topics_after_msecs
diff --git a/app/services/user_updater.rb b/app/services/user_updater.rb
index a03687c..24e0c2d 100644
--- a/app/services/user_updater.rb
+++ b/app/services/user_updater.rb
@@ -37,7 +37,8 @@ class UserUpdater
     :allow_private_messages,
     :homepage_id,
     :hide_profile_and_presence,
-    :text_size
+    :text_size,
+    :title_count_mode
   ]
 
   def initialize(actor, user)
diff --git a/config/locales/client.en.yml b/config/locales/client.en.yml
index 7d7aefd..b6ccfac 100644
--- a/config/locales/client.en.yml
+++ b/config/locales/client.en.yml
@@ -1036,6 +1036,11 @@ en:
         larger: "Larger"
         largest: "Largest"
 
+      title_count_mode:
+        title: "Background page title displays count of:"
+        notifications: "Unseen notifications"
+        contextual: "Unseen page content"
+
       like_notification_frequency:
         title: "Notify when liked"
         always: "Always"
diff --git a/config/locales/server.en.yml b/config/locales/server.en.yml
index a859b85..eeeb371 100644
--- a/config/locales/server.en.yml
+++ b/config/locales/server.en.yml
@@ -1965,6 +1965,8 @@ en:
 
     default_text_size: "Text size which is selected by default"
 
+    default_title_count_mode: "Default mode for the page title counter"
+
     retain_web_hook_events_period_days: "Number of days to retain web hook event records."
     retry_web_hook_events: "Automatically retry failed web hook events for 4 times. Time gaps between the retries are 1, 5, 25 and 125 minutes."
 
diff --git a/config/site_settings.yml b/config/site_settings.yml
index 73ccd66..00a79e6 100644
--- a/config/site_settings.yml
+++ b/config/site_settings.yml
@@ -1909,7 +1909,13 @@ user_preferences:
       - normal
       - larger
       - largest
-
+  
+  default_title_count_mode:
+    type: enum
+    default: notifications
+    choices:
+      - notifications
+      - contextual
 api:
   retain_web_hook_events_period_days:
     default: 30

[... diff too long, it was truncated ...]

GitHub sha: dc703ada

This commit has been mentioned on Discourse Meta. There might be relevant details there: