diff --git a/briar-android/res/values/color.xml b/briar-android/res/values/color.xml
index 8b0ec7923ca707bd4eaa5f1bfca10cce4f4825cf..6bf8a8abe8f57bb22b225ee83f2e17d949892d0f 100644
--- a/briar-android/res/values/color.xml
+++ b/briar-android/res/values/color.xml
@@ -11,4 +11,6 @@
 	<color name="horizontal_border">#CCCCCC</color>
 	<color name="groups_available_background">#FCCF1C</color>
 	<color name="no_posts">#AAAAAA</color>
+	<color name="settings_title_text">#2D3E50</color>
+	<color name="settings_title_underline">#2D3E50</color>
 </resources>
\ No newline at end of file
diff --git a/briar-android/res/values/strings.xml b/briar-android/res/values/strings.xml
index 9ca9365344df828d07dd6fedb184c5c25d2405d0..1664d42482f5f921d86371f639f8d528f049af9c 100644
--- a/briar-android/res/values/strings.xml
+++ b/briar-android/res/values/strings.xml
@@ -85,6 +85,15 @@
         <item quantity="other">%d new forum posts.</item>
     </plurals>
     <string name="settings_title">Settings</string>
-    <string name="activate_bluetooth_option">Activate Bluetooth while signed in</string>
-    <string name="activate_bluetooth_explanation">Briar uses Bluetooth to communicate with nearby contacts</string>
+    <string name="bluetooth_setting_title">BLUETOOTH</string>
+    <string name="bluetooth_setting">Turn on Bluetooth</string>
+    <string name="bluetooth_setting_enabled">While signed in</string>
+    <string name="bluetooth_setting_disabled">Only when adding contacts</string>
+    <string name="notification_settings_title">NOTIFICATIONS</string>
+    <string name="notify_private_messages_setting">Show alerts for private messages</string>
+    <string name="notify_group_posts_setting">Show alerts for forum posts</string>
+    <string name="notify_vibration_setting">Vibrate</string>
+    <string name="notify_sound_setting">Sound</string>
+    <string name="notify_sound_setting_enabled">Default ringtone</string>
+    <string name="notify_sound_setting_disabled">No sound</string>
 </resources>
\ No newline at end of file
diff --git a/briar-android/src/org/briarproject/android/AndroidModule.java b/briar-android/src/org/briarproject/android/AndroidModule.java
index 3f871d2c9f77f1d0ea45e38ee65ffaacc49e96f1..4192956bf456adeccd17c40690d53b5df9baeccf 100644
--- a/briar-android/src/org/briarproject/android/AndroidModule.java
+++ b/briar-android/src/org/briarproject/android/AndroidModule.java
@@ -60,8 +60,6 @@ public class AndroidModule extends AbstractModule {
 	protected void configure() {
 		bind(AndroidExecutor.class).to(AndroidExecutorImpl.class).in(
 				Singleton.class);
-		bind(AndroidNotificationManager.class).to(
-				AndroidNotificationManagerImpl.class).in(Singleton.class);
 		bind(ReferenceManager.class).to(ReferenceManagerImpl.class).in(
 				Singleton.class);
 		bind(UiCallback.class).toInstance(uiCallback);
@@ -101,4 +99,12 @@ public class AndroidModule extends AbstractModule {
 			}
 		};
 	}
+
+	@Provides @Singleton
+	AndroidNotificationManager getAndroidNotificationManager(
+			LifecycleManager lifecycleManager,
+			AndroidNotificationManagerImpl notificationManager) {
+		lifecycleManager.register(notificationManager);
+		return notificationManager;
+	}
 }
diff --git a/briar-android/src/org/briarproject/android/AndroidNotificationManagerImpl.java b/briar-android/src/org/briarproject/android/AndroidNotificationManagerImpl.java
index 7e8bc622b903a0db583da8f711ee7ad4375ed4db..c37b7b82119beafbf44023079c60218500009479 100644
--- a/briar-android/src/org/briarproject/android/AndroidNotificationManagerImpl.java
+++ b/briar-android/src/org/briarproject/android/AndroidNotificationManagerImpl.java
@@ -1,12 +1,17 @@
 package org.briarproject.android;
 
-import static android.app.Notification.DEFAULT_ALL;
+import static android.app.Notification.DEFAULT_LIGHTS;
+import static android.app.Notification.DEFAULT_SOUND;
+import static android.app.PendingIntent.FLAG_UPDATE_CURRENT;
 import static android.content.Context.NOTIFICATION_SERVICE;
 import static android.content.Intent.FLAG_ACTIVITY_NEW_TASK;
 import static android.content.Intent.FLAG_ACTIVITY_SINGLE_TOP;
+import static java.util.logging.Level.WARNING;
 
 import java.util.HashMap;
 import java.util.Map;
+import java.util.concurrent.Executor;
+import java.util.logging.Logger;
 
 import javax.inject.Inject;
 
@@ -16,21 +21,36 @@ import org.briarproject.android.contact.ConversationActivity;
 import org.briarproject.android.groups.GroupActivity;
 import org.briarproject.android.groups.GroupListActivity;
 import org.briarproject.api.ContactId;
+import org.briarproject.api.Settings;
 import org.briarproject.api.android.AndroidNotificationManager;
+import org.briarproject.api.android.DatabaseUiExecutor;
+import org.briarproject.api.db.DatabaseComponent;
+import org.briarproject.api.db.DbException;
+import org.briarproject.api.event.Event;
+import org.briarproject.api.event.EventListener;
+import org.briarproject.api.event.SettingsUpdatedEvent;
+import org.briarproject.api.lifecycle.Service;
 import org.briarproject.api.messaging.GroupId;
 
 import android.app.Application;
+import android.app.Notification;
 import android.app.NotificationManager;
 import android.content.Context;
 import android.content.Intent;
 import android.support.v4.app.NotificationCompat;
 import android.support.v4.app.TaskStackBuilder;
 
-class AndroidNotificationManagerImpl implements AndroidNotificationManager {
+class AndroidNotificationManagerImpl implements AndroidNotificationManager,
+Service, EventListener {
 
 	private static final int PRIVATE_MESSAGE_NOTIFICATION_ID = 3;
 	private static final int GROUP_POST_NOTIFICATION_ID = 4;
 
+	private static final Logger LOG =
+			Logger.getLogger(AndroidNotificationManagerImpl.class.getName());
+
+	private final DatabaseComponent db;
+	private final Executor dbUiExecutor;
 	private final Context appContext;
 	private final Map<ContactId, Integer> contactCounts =
 			new HashMap<ContactId, Integer>(); // Locking: this
@@ -39,9 +59,42 @@ class AndroidNotificationManagerImpl implements AndroidNotificationManager {
 
 	private int privateTotal = 0, groupTotal = 0; // Locking: this
 
+	private volatile Settings settings = new Settings();
+
 	@Inject
-	public AndroidNotificationManagerImpl(Application app) {
-		this.appContext = app.getApplicationContext();
+	public AndroidNotificationManagerImpl(DatabaseComponent db,
+			@DatabaseUiExecutor Executor dbExecutor, Application app) {
+		this.db = db;
+		this.dbUiExecutor = dbExecutor;
+		appContext = app.getApplicationContext();
+	}
+
+	public boolean start() {
+		db.addListener(this);
+		loadSettings();
+		return true;
+	}
+
+	private void loadSettings() {
+		dbUiExecutor.execute(new Runnable() {
+			public void run() {
+				try {
+					settings = db.getSettings();
+				} catch(DbException e) {
+					if(LOG.isLoggable(WARNING))
+						LOG.log(WARNING, e.toString(), e);
+				}
+			}
+		});
+	}
+
+	public boolean stop() {
+		db.removeListener(this);
+		return true;
+	}
+
+	public void eventOccurred(Event e) {
+		if(e instanceof SettingsUpdatedEvent) loadSettings();
 	}
 
 	public synchronized void showPrivateMessageNotification(ContactId c) {
@@ -63,6 +116,8 @@ class AndroidNotificationManagerImpl implements AndroidNotificationManager {
 	private void updatePrivateMessageNotification() {
 		if(privateTotal == 0) {
 			clearPrivateMessageNotification();
+		} else if(!settings.getBoolean("notifyPrivateMessages", true)) {
+			return;
 		} else {
 			NotificationCompat.Builder b =
 					new NotificationCompat.Builder(appContext);
@@ -71,24 +126,24 @@ class AndroidNotificationManagerImpl implements AndroidNotificationManager {
 			b.setContentText(appContext.getResources().getQuantityString(
 					R.plurals.private_message_notification_text, privateTotal,
 					privateTotal));
-			b.setDefaults(DEFAULT_ALL);
+			b.setDefaults(getDefaults());
 			b.setOnlyAlertOnce(true);
 			if(contactCounts.size() == 1) {
 				Intent i = new Intent(appContext, ConversationActivity.class);
 				ContactId c = contactCounts.keySet().iterator().next();
 				i.putExtra("briar.CONTACT_ID", c.getInt());
 				i.setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_SINGLE_TOP);
-				TaskStackBuilder tsb = TaskStackBuilder.create(appContext);
-				tsb.addParentStack(ConversationActivity.class);
-				tsb.addNextIntent(i);
-				b.setContentIntent(tsb.getPendingIntent(0, 0));
+				TaskStackBuilder t = TaskStackBuilder.create(appContext);
+				t.addParentStack(ConversationActivity.class);
+				t.addNextIntent(i);
+				b.setContentIntent(t.getPendingIntent(0, FLAG_UPDATE_CURRENT));
 			} else {
 				Intent i = new Intent(appContext, ContactListActivity.class);
 				i.setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_SINGLE_TOP);
-				TaskStackBuilder tsb = TaskStackBuilder.create(appContext);
-				tsb.addParentStack(ContactListActivity.class);
-				tsb.addNextIntent(i);
-				b.setContentIntent(tsb.getPendingIntent(0, 0));
+				TaskStackBuilder t = TaskStackBuilder.create(appContext);
+				t.addParentStack(ContactListActivity.class);
+				t.addNextIntent(i);
+				b.setContentIntent(t.getPendingIntent(0, FLAG_UPDATE_CURRENT));
 			}
 			Object o = appContext.getSystemService(NOTIFICATION_SERVICE);
 			NotificationManager nm = (NotificationManager) o;
@@ -103,6 +158,15 @@ class AndroidNotificationManagerImpl implements AndroidNotificationManager {
 		nm.cancel(PRIVATE_MESSAGE_NOTIFICATION_ID);
 	}
 
+	private int getDefaults() {
+		int defaults = DEFAULT_LIGHTS;
+		if(settings.getBoolean("notifySound", true))
+			defaults |= DEFAULT_SOUND;
+		if(settings.getBoolean("notifyVibration", true))
+			defaults |= Notification.DEFAULT_VIBRATE;
+		return defaults;
+	}
+
 	public synchronized void showGroupPostNotification(GroupId g) {
 		Integer count = groupCounts.get(g);
 		if(count == null) groupCounts.put(g, 1);
@@ -122,6 +186,8 @@ class AndroidNotificationManagerImpl implements AndroidNotificationManager {
 	private void updateGroupPostNotification() {
 		if(groupTotal == 0) {
 			clearGroupPostNotification();
+		} else if(!settings.getBoolean("notifyGroupPosts", true)) {
+			return;
 		} else {
 			NotificationCompat.Builder b =
 					new NotificationCompat.Builder(appContext);
@@ -130,24 +196,24 @@ class AndroidNotificationManagerImpl implements AndroidNotificationManager {
 			b.setContentText(appContext.getResources().getQuantityString(
 					R.plurals.group_post_notification_text, groupTotal,
 					groupTotal));
-			b.setDefaults(DEFAULT_ALL);
+			b.setDefaults(getDefaults());
 			b.setOnlyAlertOnce(true);
 			if(groupCounts.size() == 1) {
 				Intent i = new Intent(appContext, GroupActivity.class);
 				GroupId g = groupCounts.keySet().iterator().next();
 				i.putExtra("briar.GROUP_ID", g.getBytes());
 				i.setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_SINGLE_TOP);
-				TaskStackBuilder tsb = TaskStackBuilder.create(appContext);
-				tsb.addParentStack(GroupActivity.class);
-				tsb.addNextIntent(i);
-				b.setContentIntent(tsb.getPendingIntent(0, 0));
+				TaskStackBuilder t = TaskStackBuilder.create(appContext);
+				t.addParentStack(GroupActivity.class);
+				t.addNextIntent(i);
+				b.setContentIntent(t.getPendingIntent(0, FLAG_UPDATE_CURRENT));
 			} else {
 				Intent i = new Intent(appContext, GroupListActivity.class);
 				i.setFlags(FLAG_ACTIVITY_NEW_TASK | FLAG_ACTIVITY_SINGLE_TOP);
-				TaskStackBuilder tsb = TaskStackBuilder.create(appContext);
-				tsb.addParentStack(GroupListActivity.class);
-				tsb.addNextIntent(i);
-				b.setContentIntent(tsb.getPendingIntent(0, 0));
+				TaskStackBuilder t = TaskStackBuilder.create(appContext);
+				t.addParentStack(GroupListActivity.class);
+				t.addNextIntent(i);
+				b.setContentIntent(t.getPendingIntent(0, FLAG_UPDATE_CURRENT));
 			}
 			Object o = appContext.getSystemService(NOTIFICATION_SERVICE);
 			NotificationManager nm = (NotificationManager) o;
diff --git a/briar-android/src/org/briarproject/android/PasswordActivity.java b/briar-android/src/org/briarproject/android/PasswordActivity.java
index 22791219ca91785ecdffa836da54fafc556689cb..0c852a05a7c4ca9b4b8ba06c8f12ef63266be18e 100644
--- a/briar-android/src/org/briarproject/android/PasswordActivity.java
+++ b/briar-android/src/org/briarproject/android/PasswordActivity.java
@@ -95,9 +95,7 @@ public class PasswordActivity extends RoboActivity {
 		layout.addView(passwordEntry);
 
 		// Adjusting the padding of buttons and EditTexts has the wrong results
-		FixedVerticalSpace space = new FixedVerticalSpace(this);
-		space.setHeight(pad);
-		layout.addView(space);
+		layout.addView(new FixedVerticalSpace(this));
 
 		continueButton = new Button(this);
 		continueButton.setLayoutParams(WRAP_WRAP);
diff --git a/briar-android/src/org/briarproject/android/SettingsActivity.java b/briar-android/src/org/briarproject/android/SettingsActivity.java
index bb01b8900eabbab117155477fc8d7cb2fc00cc39..e64d901c9444b2e4bcc3cea996768d66749b6aab 100644
--- a/briar-android/src/org/briarproject/android/SettingsActivity.java
+++ b/briar-android/src/org/briarproject/android/SettingsActivity.java
@@ -1,9 +1,11 @@
 package org.briarproject.android;
 
+import static android.graphics.Typeface.DEFAULT_BOLD;
 import static android.view.Gravity.CENTER;
 import static android.view.View.GONE;
 import static android.view.View.VISIBLE;
 import static android.widget.LinearLayout.VERTICAL;
+import static java.util.logging.Level.INFO;
 import static java.util.logging.Level.WARNING;
 import static org.briarproject.android.util.CommonLayoutParams.MATCH_WRAP;
 import static org.briarproject.android.util.CommonLayoutParams.MATCH_WRAP_1;
@@ -16,10 +18,14 @@ import org.briarproject.R;
 import org.briarproject.android.util.HorizontalBorder;
 import org.briarproject.android.util.LayoutUtils;
 import org.briarproject.android.util.ListLoadingProgressBar;
+import org.briarproject.api.Settings;
 import org.briarproject.api.TransportConfig;
 import org.briarproject.api.TransportId;
 import org.briarproject.api.db.DatabaseComponent;
 import org.briarproject.api.db.DbException;
+import org.briarproject.api.event.Event;
+import org.briarproject.api.event.EventListener;
+import org.briarproject.api.event.SettingsUpdatedEvent;
 
 import android.bluetooth.BluetoothAdapter;
 import android.content.Intent;
@@ -33,15 +39,20 @@ import android.widget.LinearLayout;
 import android.widget.ScrollView;
 import android.widget.TextView;
 
-public class SettingsActivity extends BriarActivity implements OnClickListener {
+public class SettingsActivity extends BriarActivity implements EventListener,
+OnClickListener {
 
 	private static final Logger LOG =
 			Logger.getLogger(SettingsActivity.class.getName());
 
-	private CheckBox bluetooth = null;
 	private ScrollView scroll = null;
+	private TextView enableBluetooth = null, enableBluetoothHint = null;
+	private CheckBox notifyPrivateMessages = null, notifyGroupPosts = null;
+	private CheckBox notifyVibration = null;
+	private TextView notifySound = null, notifySoundHint = null;
 	private ListLoadingProgressBar progress = null;
 	private ImageButton testingButton = null;
+	private boolean bluetoothSetting = true, soundSetting = true;
 
 	// Fields that are accessed from background threads must be volatile
 	@Inject private volatile DatabaseComponent db;
@@ -60,16 +71,87 @@ public class SettingsActivity extends BriarActivity implements OnClickListener {
 		int pad = LayoutUtils.getPadding(this);
 		settings.setPadding(pad, pad, pad, pad);
 
-		bluetooth = new CheckBox(this);
-		bluetooth.setLayoutParams(MATCH_WRAP);
-		bluetooth.setTextSize(18);
-		bluetooth.setText(R.string.activate_bluetooth_option);
-		bluetooth.setOnClickListener(this);
-		settings.addView(bluetooth);
+		TextView bluetoothTitle = new TextView(this);
+		bluetoothTitle.setPadding(pad, 0, pad, 0);
+		bluetoothTitle.setTypeface(DEFAULT_BOLD);
+		Resources res = getResources();
+		int titleText = res.getColor(R.color.settings_title_text);
+		bluetoothTitle.setTextColor(titleText);
+		bluetoothTitle.setText(R.string.bluetooth_setting_title);
+		settings.addView(bluetoothTitle);
+
+		HorizontalBorder underline = new HorizontalBorder(this);
+		int titleUnderline = res.getColor(R.color.settings_title_underline);
+		underline.setBackgroundColor(titleUnderline);
+		settings.addView(underline);
+
+		enableBluetooth = new TextView(this);
+		enableBluetooth.setPadding(pad, pad, pad, 0);
+		enableBluetooth.setTextSize(18);
+		enableBluetooth.setText(R.string.bluetooth_setting);
+		enableBluetooth.setOnClickListener(this);
+		settings.addView(enableBluetooth);
+
+		enableBluetoothHint = new TextView(this);
+		enableBluetoothHint.setPadding(pad, 0, pad, pad);
+		enableBluetoothHint.setText(R.string.bluetooth_setting_enabled);
+		enableBluetoothHint.setOnClickListener(this);
+		settings.addView(enableBluetoothHint);
+
+		TextView notificationsTitle = new TextView(this);
+		notificationsTitle.setPadding(pad, 0, pad, 0);
+		notificationsTitle.setTypeface(DEFAULT_BOLD);
+		notificationsTitle.setTextColor(titleText);
+		notificationsTitle.setText(R.string.notification_settings_title);
+		settings.addView(notificationsTitle);
+
+		underline = new HorizontalBorder(this);
+		underline.setBackgroundColor(titleUnderline);
+		settings.addView(underline);
+
+		notifyPrivateMessages = new CheckBox(this);
+		notifyPrivateMessages.setPadding(0, pad, 0, pad);
+		notifyPrivateMessages.setTextSize(18);
+		notifyPrivateMessages.setText(R.string.notify_private_messages_setting);
+		notifyPrivateMessages.setChecked(true);
+		notifyPrivateMessages.setOnClickListener(this);
+		settings.addView(notifyPrivateMessages);
+
+		settings.addView(new HorizontalBorder(this));
 
-		TextView bluetoothHint = new TextView(this);
-		bluetoothHint.setText(R.string.activate_bluetooth_explanation);
-		settings.addView(bluetoothHint);
+		notifyGroupPosts = new CheckBox(this);
+		notifyGroupPosts.setPadding(0, pad, 0, pad);
+		notifyGroupPosts.setTextSize(18);
+		notifyGroupPosts.setText(R.string.notify_group_posts_setting);
+		notifyGroupPosts.setChecked(true);
+		notifyGroupPosts.setOnClickListener(this);
+		settings.addView(notifyGroupPosts);
+
+		settings.addView(new HorizontalBorder(this));
+
+		notifyVibration = new CheckBox(this);
+		notifyVibration.setPadding(0, pad, 0, pad);
+		notifyVibration.setTextSize(18);
+		notifyVibration.setText(R.string.notify_vibration_setting);
+		notifyVibration.setOnClickListener(this);
+		settings.addView(notifyVibration);
+
+		settings.addView(new HorizontalBorder(this));
+
+		notifySound = new TextView(this);
+		notifySound.setPadding(pad, pad, pad, 0);
+		notifySound.setTextSize(18);
+		notifySound.setText(R.string.notify_sound_setting);
+		notifySound.setOnClickListener(this);
+		settings.addView(notifySound);
+
+		notifySoundHint = new TextView(this);
+		notifySoundHint.setPadding(pad, 0, pad, pad);
+		notifySoundHint.setText(R.string.notify_sound_setting_enabled);
+		notifySoundHint.setOnClickListener(this);
+		settings.addView(notifySoundHint);
+
+		settings.addView(new HorizontalBorder(this));
 
 		scroll.addView(settings);
 		scroll.setLayoutParams(MATCH_WRAP_1);
@@ -84,7 +166,6 @@ public class SettingsActivity extends BriarActivity implements OnClickListener {
 		LinearLayout footer = new LinearLayout(this);
 		footer.setLayoutParams(MATCH_WRAP);
 		footer.setGravity(CENTER);
-		Resources res = getResources();
 		footer.setBackgroundColor(res.getColor(R.color.button_bar_background));
 		testingButton = new ImageButton(this);
 		testingButton.setBackgroundResource(0);
@@ -99,6 +180,7 @@ public class SettingsActivity extends BriarActivity implements OnClickListener {
 	@Override
 	public void onResume() {
 		super.onResume();
+		db.addListener(this);
 		loadSettings();
 	}
 
@@ -106,11 +188,14 @@ public class SettingsActivity extends BriarActivity implements OnClickListener {
 		runOnDbThread(new Runnable() {
 			public void run() {
 				try {
-					boolean activateBluetooth = true;
+					long now = System.currentTimeMillis();
 					TransportConfig c = db.getConfig(new TransportId("bt"));
-					if(c != null && "false".equals(c.get("enable")))
-						activateBluetooth = false;
-					displaySettings(activateBluetooth);
+					Settings settings = db.getSettings();
+					long duration = System.currentTimeMillis() - now;
+					if(LOG.isLoggable(INFO))
+						LOG.info("Loading settings took " + duration + " ms");
+					boolean btSetting = c.getBoolean("enable", true);
+					displaySettings(btSetting, settings);
 				} catch(DbException e) {
 					if(LOG.isLoggable(WARNING))
 						LOG.log(WARNING, e.toString(), e);
@@ -119,37 +204,82 @@ public class SettingsActivity extends BriarActivity implements OnClickListener {
 		});
 	}
 
-	private void displaySettings(final boolean activateBluetooth) {
+	private void displaySettings(final boolean btSetting,
+			final Settings settings) {
 		runOnUiThread(new Runnable() {
 			public void run() {
 				scroll.setVisibility(VISIBLE);
 				progress.setVisibility(GONE);
-				bluetooth.setChecked(activateBluetooth);
+
+				bluetoothSetting = btSetting;
+				int resId;
+				if(bluetoothSetting) resId = R.string.bluetooth_setting_enabled;
+				else resId = R.string.bluetooth_setting_disabled;
+				enableBluetoothHint.setText(resId);
+
+				notifyPrivateMessages.setChecked(settings.getBoolean(
+						"notifyPrivateMessages", true));
+
+				notifyGroupPosts.setChecked(settings.getBoolean(
+						"notifyGroupPosts", true));
+
+				notifyVibration.setChecked(settings.getBoolean(
+						"notifyVibration", true));
+
+				soundSetting = settings.getBoolean("notifySound", true);
+				if(soundSetting) resId = R.string.notify_sound_setting_enabled;
+				else resId = R.string.notify_sound_setting_disabled;
+				notifySoundHint.setText(resId);
 			}
 		});
 	}
 
+	@Override
+	public void onPause() {
+		super.onPause();
+		db.removeListener(this);
+	}
+
 	public void onClick(View view) {
 		if(testingButton == null) return; // Not created yet
-		if(view == bluetooth) {
-			boolean activateBluetooth = bluetooth.isChecked();
-			if(!activateBluetooth) {
-				BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter();
-				if(adapter != null) adapter.disable();
-			}
-			storeSettings(activateBluetooth);
-		} else if(view == testingButton) {
+		if(view == testingButton) {
 			startActivity(new Intent(this, TestingActivity.class));
+			return;
+		}
+		if(view == enableBluetooth || view == enableBluetoothHint) {
+			bluetoothSetting = !bluetoothSetting;
+			BluetoothAdapter adapter = BluetoothAdapter.getDefaultAdapter();
+			if(adapter != null) {
+				if(bluetoothSetting) adapter.enable();
+				else adapter.disable();
+			}
+		} else if(view == notifySound || view == notifySoundHint) {
+			soundSetting = !soundSetting;
 		}
+		Settings settings = new Settings();
+		settings.putBoolean("notifyPrivateMessages",
+				notifyPrivateMessages.isChecked());
+		settings.putBoolean("notifyGroupPosts",
+				notifyGroupPosts.isChecked());
+		settings.putBoolean("notifyVibration",
+				notifyVibration.isChecked());
+		settings.putBoolean("notifySound", soundSetting);
+		storeSettings(bluetoothSetting, settings);
 	}
 
-	private void storeSettings(final boolean activateBluetooth) {
+	private void storeSettings(final boolean btSetting,
+			final Settings settings) {
 		runOnDbThread(new Runnable() {
 			public void run() {
 				try {
 					TransportConfig c = new TransportConfig();
-					c.put("enable", String.valueOf(activateBluetooth));
+					c.putBoolean("enable", btSetting);
+					long now = System.currentTimeMillis();
 					db.mergeConfig(new TransportId("bt"), c);
+					db.mergeSettings(settings);
+					long duration = System.currentTimeMillis() - now;
+					if(LOG.isLoggable(INFO))
+						LOG.info("Storing settings took " + duration + " ms");
 				} catch(DbException e) {
 					if(LOG.isLoggable(WARNING))
 						LOG.log(WARNING, e.toString(), e);
@@ -157,4 +287,11 @@ public class SettingsActivity extends BriarActivity implements OnClickListener {
 			}
 		});
 	}
+
+	public void eventOccurred(Event e) {
+		if(e instanceof SettingsUpdatedEvent) {
+			LOG.info("Settings updated");
+			loadSettings();
+		}
+	}
 }
diff --git a/briar-android/src/org/briarproject/android/SetupActivity.java b/briar-android/src/org/briarproject/android/SetupActivity.java
index 261c6a4e41131dc7d92915f4dd3559ce153d2bb0..2c1a0932ac507219b5bd623f37051ec460874b9c 100644
--- a/briar-android/src/org/briarproject/android/SetupActivity.java
+++ b/briar-android/src/org/briarproject/android/SetupActivity.java
@@ -234,33 +234,33 @@ public class SetupActivity extends RoboActivity implements OnClickListener {
 	}
 
 	private void storeEncryptedDatabaseKey(final byte[] encrypted) {
-		long start = System.currentTimeMillis();
+		long now = System.currentTimeMillis();
 		SharedPreferences prefs = getSharedPreferences("db", MODE_PRIVATE);
 		Editor editor = prefs.edit();
 		editor.putString("key", StringUtils.toHexString(encrypted));
 		editor.commit();
-		long duration = System.currentTimeMillis() - start;
+		long duration = System.currentTimeMillis() - now;
 		if(LOG.isLoggable(INFO))
 			LOG.info("Key storage took " + duration + " ms");
 	}
 
 	private byte[] encryptDatabaseKey(byte[] key, char[] password) {
-		long start = System.currentTimeMillis();
+		long now = System.currentTimeMillis();
 		byte[] encrypted = crypto.encryptWithPassword(key, password);
-		long duration = System.currentTimeMillis() - start;
+		long duration = System.currentTimeMillis() - now;
 		if(LOG.isLoggable(INFO))
 			LOG.info("Key derivation took " + duration + " ms");
 		return encrypted;
 	}
 
 	private LocalAuthor createLocalAuthor(String nickname) {
-		long start = System.currentTimeMillis();
+		long now = System.currentTimeMillis();
 		KeyPair keyPair = crypto.generateSignatureKeyPair();
 		byte[] publicKey = keyPair.getPublic().getEncoded();
 		byte[] privateKey = keyPair.getPrivate().getEncoded();
 		LocalAuthor localAuthor = authorFactory.createLocalAuthor(nickname,
 				publicKey, privateKey);
-		long duration = System.currentTimeMillis() - start;
+		long duration = System.currentTimeMillis() - now;
 		if(LOG.isLoggable(INFO))
 			LOG.info("Identity creation took " + duration + " ms");
 		return localAuthor;
diff --git a/briar-android/src/org/briarproject/android/SplashScreenActivity.java b/briar-android/src/org/briarproject/android/SplashScreenActivity.java
index e8040226e0049082fef8a78539beea2c34e69ffa..7c9adcabd261cc3ee4cd8e0bf43b9460c573571a 100644
--- a/briar-android/src/org/briarproject/android/SplashScreenActivity.java
+++ b/briar-android/src/org/briarproject/android/SplashScreenActivity.java
@@ -33,7 +33,7 @@ public class SplashScreenActivity extends RoboSplashActivity {
 	// Default log level - change this to OFF for release builds
 	private static final Level DEFAULT_LOG_LEVEL = INFO;
 
-	private long start = System.currentTimeMillis();
+	private long now = System.currentTimeMillis();
 
 	public SplashScreenActivity() {
 		Logger.getLogger("").setLevel(DEFAULT_LOG_LEVEL);
@@ -60,7 +60,7 @@ public class SplashScreenActivity extends RoboSplashActivity {
 	}
 
 	protected void startNextActivity() {
-		long duration = System.currentTimeMillis() - start;
+		long duration = System.currentTimeMillis() - now;
 		if(LOG.isLoggable(INFO))
 			LOG.info("Guice startup took " + duration + " ms");
 		if(System.currentTimeMillis() >= EXPIRY_DATE) {
diff --git a/briar-android/src/org/briarproject/android/util/FixedVerticalSpace.java b/briar-android/src/org/briarproject/android/util/FixedVerticalSpace.java
index e9625f348451784067e8a793424238205fcc9d5f..2ef076fda97c4ccd4b420881ba4842f986ac6601 100644
--- a/briar-android/src/org/briarproject/android/util/FixedVerticalSpace.java
+++ b/briar-android/src/org/briarproject/android/util/FixedVerticalSpace.java
@@ -1,6 +1,6 @@
 package org.briarproject.android.util;
 
-import static android.view.ViewGroup.LayoutParams.WRAP_CONTENT;
+import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
 import android.content.Context;
 import android.view.View;
 import android.view.ViewGroup.LayoutParams;
@@ -9,9 +9,7 @@ public class FixedVerticalSpace extends View {
 
 	public FixedVerticalSpace(Context ctx) {
 		super(ctx);
-	}
-
-	public void setHeight(int height) {
-		setLayoutParams(new LayoutParams(WRAP_CONTENT, height));
+		int height = LayoutUtils.getPadding(ctx);
+		setLayoutParams(new LayoutParams(MATCH_PARENT, height));
 	}
 }
diff --git a/briar-android/src/org/briarproject/plugins/AndroidPluginsModule.java b/briar-android/src/org/briarproject/plugins/AndroidPluginsModule.java
index 9a3b9ce3c208be9b40fe80ab271ef0648acab838..7fa8a4b39d25a7eec7ec0afbe7da85bcc0a96b28 100644
--- a/briar-android/src/org/briarproject/plugins/AndroidPluginsModule.java
+++ b/briar-android/src/org/briarproject/plugins/AndroidPluginsModule.java
@@ -43,11 +43,12 @@ public class AndroidPluginsModule extends AbstractModule {
 			AndroidExecutor androidExecutor, Application app,
 			CryptoComponent crypto, LocationUtils locationUtils,
 			ShutdownManager shutdownManager) {
-		Context ctx = app.getApplicationContext();
+		Context appContext = app.getApplicationContext();
 		DuplexPluginFactory droidtooth = new DroidtoothPluginFactory(
-				pluginExecutor, androidExecutor, ctx, crypto.getSecureRandom());
+				pluginExecutor, androidExecutor, appContext,
+				crypto.getSecureRandom());
 		DuplexPluginFactory tor = new TorPluginFactory(pluginExecutor,
-				ctx, locationUtils, shutdownManager);
+				appContext, locationUtils, shutdownManager);
 		DuplexPluginFactory lan = new LanTcpPluginFactory(pluginExecutor);
 		final Collection<DuplexPluginFactory> factories =
 				Arrays.asList(droidtooth, tor, lan);
diff --git a/briar-android/src/org/briarproject/plugins/droidtooth/DroidtoothPlugin.java b/briar-android/src/org/briarproject/plugins/droidtooth/DroidtoothPlugin.java
index 4045048ff68aea6fb5148b5cb1641735753da4ee..c87da27f73fb2ddd5f347de398c4c7f5b1ce82d0 100644
--- a/briar-android/src/org/briarproject/plugins/droidtooth/DroidtoothPlugin.java
+++ b/briar-android/src/org/briarproject/plugins/droidtooth/DroidtoothPlugin.java
@@ -155,8 +155,7 @@ class DroidtoothPlugin implements DuplexPlugin {
 
 	private boolean enableBluetooth() {
 		if(adapter.isEnabled()) return true;
-		String enable = callback.getConfig().get("enable");
-		if("false".equals(enable)) {
+		if(!callback.getConfig().getBoolean("enable", true)) {
 			if(LOG.isLoggable(INFO)) LOG.info("Not enabling Bluetooth");
 			return false;
 		}
@@ -267,7 +266,7 @@ class DroidtoothPlugin implements DuplexPlugin {
 
 	public void poll(Collection<ContactId> connected) {
 		if(!running) return;
-		if(!enableBluetooth()) return;
+		if(!adapter.isEnabled()) return;
 		// Try to connect to known devices in parallel
 		Map<ContactId, TransportProperties> remote =
 				callback.getRemoteProperties();
@@ -349,7 +348,7 @@ class DroidtoothPlugin implements DuplexPlugin {
 	public DuplexTransportConnection createInvitationConnection(PseudoRandom r,
 			long timeout) {
 		if(!running) return null;
-		if(!enableBluetooth()) return null;
+		if(!adapter.isEnabled()) return null;
 		// Use the invitation codes to generate the UUID
 		byte[] b = r.nextBytes(UUID_BYTES);
 		UUID uuid = UUID.nameUUIDFromBytes(b);