Merge pull request #2516 from PhilippC/803--totp-overview
TOTP overview
This commit is contained in:
@@ -72,8 +72,9 @@ namespace keepass2android
|
||||
}
|
||||
|
||||
private IDatabaseFormat _databaseFormat = new KdbxDatabaseFormat(KdbxFormat.Default);
|
||||
private bool? _hasTotpEntries;
|
||||
|
||||
public bool ReloadRequested { get; set; }
|
||||
public bool ReloadRequested { get; set; }
|
||||
|
||||
public bool DidOpenFileChange()
|
||||
{
|
||||
@@ -104,8 +105,9 @@ namespace keepass2android
|
||||
SearchHelper = new SearchDbHelper(app);
|
||||
|
||||
_databaseFormat = databaseFormat;
|
||||
_hasTotpEntries = null;
|
||||
|
||||
CanWrite = databaseFormat.CanWrite && !fileStorage.IsReadOnly(iocInfo);
|
||||
CanWrite = databaseFormat.CanWrite && !fileStorage.IsReadOnly(iocInfo);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -200,8 +202,21 @@ namespace keepass2android
|
||||
|
||||
trans.CommitWrite();
|
||||
}
|
||||
|
||||
}
|
||||
_hasTotpEntries = null;
|
||||
|
||||
}
|
||||
|
||||
public bool HasTotpEntries
|
||||
{
|
||||
get
|
||||
{
|
||||
if (_hasTotpEntries == null)
|
||||
{
|
||||
_hasTotpEntries = true;
|
||||
}
|
||||
return _hasTotpEntries.Value;
|
||||
}
|
||||
}
|
||||
|
||||
private void PopulateGlobals(PwGroup currentGroup, bool checkForDuplicateUuids )
|
||||
{
|
||||
|
@@ -39,6 +39,9 @@ using Android.Support.V4.View;
|
||||
using Android.Views.Autofill;
|
||||
using CursorAdapter = Android.Support.V4.Widget.CursorAdapter;
|
||||
using Object = Java.Lang.Object;
|
||||
using Android.Text;
|
||||
using keepass2android.search;
|
||||
using KeeTrayTOTP.Libraries;
|
||||
|
||||
namespace keepass2android
|
||||
{
|
||||
@@ -115,6 +118,8 @@ namespace keepass2android
|
||||
FindViewById(Resource.Id.fabAddNewEntry).Visibility = ViewStates.Gone;
|
||||
|
||||
FindViewById(Resource.Id.fabAddNew).Visibility = (showAddGroup || showAddEntry) ? ViewStates.Visible : ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabSearch).Visibility = (showAddGroup || showAddEntry) ? ViewStates.Visible : ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabTotpOverview).Visibility = CanShowTotpFab() ? ViewStates.Visible : ViewStates.Gone;
|
||||
}
|
||||
|
||||
UpdateBottomBarElementVisibility(Resource.Id.insert_element, false);
|
||||
@@ -262,6 +267,7 @@ namespace keepass2android
|
||||
private bool hasCalledOtherActivity = false;
|
||||
private IMenuItem searchItem;
|
||||
private IMenuItem searchItemDummy;
|
||||
private bool isPaused;
|
||||
|
||||
protected override void OnResume()
|
||||
{
|
||||
@@ -281,8 +287,39 @@ namespace keepass2android
|
||||
RefreshIfDirty();
|
||||
|
||||
SetSearchItemVisibility();
|
||||
}
|
||||
|
||||
isPaused = false;
|
||||
System.Threading.Tasks.Task.Run(UpdateTotpCountdown);
|
||||
}
|
||||
private async System.Threading.Tasks.Task UpdateTotpCountdown()
|
||||
{
|
||||
|
||||
while (!isPaused )
|
||||
{
|
||||
RunOnUiThread(() =>
|
||||
{
|
||||
var listView = FragmentManager.FindFragmentById<GroupListFragment>(Resource.Id.list_fragment)
|
||||
.ListView;
|
||||
if (listView != null)
|
||||
{
|
||||
int count = listView.Count;
|
||||
for (int i = 0; i < count; i++)
|
||||
{
|
||||
var item = listView.GetChildAt(i);
|
||||
if (item is PwEntryView)
|
||||
{
|
||||
var entryView = (PwEntryView)item;
|
||||
entryView.UpdateTotp();
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
|
||||
await System.Threading.Tasks.Task.Delay(1000);
|
||||
}
|
||||
}
|
||||
|
||||
private void UpdateInfotexts()
|
||||
{
|
||||
@@ -390,6 +427,13 @@ namespace keepass2android
|
||||
}
|
||||
|
||||
|
||||
protected override void OnPause()
|
||||
{
|
||||
base.OnPause();
|
||||
isPaused = true;
|
||||
}
|
||||
|
||||
|
||||
private void UpdatePostNotificationsPermissionInfo(bool hideForever=false)
|
||||
{
|
||||
const string prefsKey = "DidShowNotificationPermissionInfo";
|
||||
@@ -572,6 +616,25 @@ namespace keepass2android
|
||||
};
|
||||
}
|
||||
|
||||
if (FindViewById(Resource.Id.fabSearch) != null)
|
||||
{
|
||||
FindViewById(Resource.Id.fabSearch).Click += (sender, args) =>
|
||||
{
|
||||
if (searchView?.Iconified != false)
|
||||
ActivateSearchView();
|
||||
else
|
||||
searchView.Iconified = true;
|
||||
};
|
||||
}
|
||||
|
||||
if (FindViewById(Resource.Id.fabTotpOverview) != null)
|
||||
{
|
||||
FindViewById(Resource.Id.fabTotpOverview).Click += (sender, args) =>
|
||||
{
|
||||
SearchTotpResults.Launch(this, this.AppTask);
|
||||
};
|
||||
}
|
||||
|
||||
if (FindViewById(Resource.Id.fabCancelAddNew) != null)
|
||||
{
|
||||
FindViewById(Resource.Id.fabAddNew).Click += (sender, args) =>
|
||||
@@ -580,6 +643,8 @@ namespace keepass2android
|
||||
FindViewById(Resource.Id.fabAddNewGroup).Visibility = AddGroupEnabled ? ViewStates.Visible : ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabAddNewEntry).Visibility = AddEntryEnabled ? ViewStates.Visible : ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabAddNew).Visibility = ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabSearch).Visibility = ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabTotpOverview).Visibility = ViewStates.Gone;
|
||||
};
|
||||
|
||||
FindViewById(Resource.Id.fabCancelAddNew).Click += (sender, args) =>
|
||||
@@ -588,6 +653,8 @@ namespace keepass2android
|
||||
FindViewById(Resource.Id.fabAddNewGroup).Visibility = ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabAddNewEntry).Visibility = ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabAddNew).Visibility = ViewStates.Visible;
|
||||
FindViewById(Resource.Id.fabSearch).Visibility = ViewStates.Visible;
|
||||
FindViewById(Resource.Id.fabTotpOverview).Visibility = CanShowTotpFab() ? ViewStates.Visible : ViewStates.Gone;
|
||||
};
|
||||
|
||||
|
||||
@@ -667,7 +734,12 @@ namespace keepass2android
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
protected virtual bool CanShowTotpFab()
|
||||
{
|
||||
return App.Kp2a.CurrentDb.HasTotpEntries && Group == App.Kp2a.CurrentDb.Root;
|
||||
}
|
||||
|
||||
private bool IsTimeForInfotext(out string lastInfoText)
|
||||
{
|
||||
DateTime lastDisplayTime = new DateTime(_prefs.GetLong("LastInfoTextTime", 0));
|
||||
@@ -1028,6 +1100,7 @@ namespace keepass2android
|
||||
|
||||
searchView.Iconified = false;
|
||||
AppTask.CanActivateSearchViewOnStart = false;
|
||||
|
||||
|
||||
}
|
||||
|
||||
@@ -1067,6 +1140,15 @@ namespace keepass2android
|
||||
|
||||
public abstract ElementAndDatabaseId FullGroupId { get; }
|
||||
|
||||
public virtual bool MayPreviewTotp
|
||||
{
|
||||
get
|
||||
{
|
||||
return !PreferenceManager.GetDefaultSharedPreferences(this).GetBoolean(GetString(Resource.String.masktotp_key),
|
||||
Resources.GetBoolean(Resource.Boolean.masktotp_default));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public override bool OnPrepareOptionsMenu(IMenu menu)
|
||||
{
|
||||
@@ -1267,6 +1349,7 @@ namespace keepass2android
|
||||
FindViewById(Resource.Id.fabAddNewGroup).Visibility = ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabAddNewEntry).Visibility = ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabAddNew).Visibility = ViewStates.Gone;
|
||||
FindViewById(Resource.Id.fabSearch).Visibility = ViewStates.Gone;
|
||||
|
||||
UpdateBottomBarElementVisibility(Resource.Id.insert_element, true);
|
||||
UpdateBottomBarElementVisibility(Resource.Id.cancel_insert_element, true);
|
||||
@@ -1330,6 +1413,7 @@ namespace keepass2android
|
||||
}
|
||||
|
||||
ListView.ItemClick += (sender, args) => ((GroupListItemView)args.View).OnClick();
|
||||
|
||||
|
||||
StyleListView();
|
||||
|
||||
|
BIN
src/keepass2android/Resources/drawable-mdpi/ic_fab_search.png
Normal file
BIN
src/keepass2android/Resources/drawable-mdpi/ic_fab_search.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 9.9 KiB |
BIN
src/keepass2android/Resources/drawable-mdpi/ic_fab_totp.png
Normal file
BIN
src/keepass2android/Resources/drawable-mdpi/ic_fab_totp.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 8.3 KiB |
BIN
src/keepass2android/Resources/drawable-xhdpi/ic_fab_search.png
Normal file
BIN
src/keepass2android/Resources/drawable-xhdpi/ic_fab_search.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 11 KiB |
BIN
src/keepass2android/Resources/drawable-xhdpi/ic_fab_totp.png
Normal file
BIN
src/keepass2android/Resources/drawable-xhdpi/ic_fab_totp.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 6.3 KiB |
@@ -61,6 +61,28 @@
|
||||
android:layout_width="wrap_content"
|
||||
android:text="group detail"
|
||||
style="@style/GroupDetailInSearchResult" />
|
||||
|
||||
<LinearLayout
|
||||
android:id="@+id/totp_layout"
|
||||
android:layout_width="fill_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:orientation="vertical">
|
||||
|
||||
<TextView
|
||||
android:id="@+id/totp_text"
|
||||
android:layout_height="match_parent"
|
||||
android:layout_width="wrap_content"
|
||||
android:text=""/>
|
||||
|
||||
<ProgressBar
|
||||
android:id="@+id/TotpCountdownProgressBar"
|
||||
style="?android:attr/progressBarStyleHorizontal"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_alignParentTop="true"
|
||||
android:layout_alignParentBottom="true"
|
||||
android:layout_marginRight="30dp" />
|
||||
</LinearLayout>
|
||||
</LinearLayout>
|
||||
|
||||
<ImageView android:id="@+id/right_arrow"
|
||||
|
@@ -400,5 +400,23 @@
|
||||
android:layout_marginRight="16dp"
|
||||
android:layout_marginBottom="160dp"
|
||||
android:visibility="gone"/>
|
||||
<android.support.design.widget.FloatingActionButton
|
||||
android:id="@+id/fabSearch"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="end|bottom|right"
|
||||
android:src="@drawable/ic_fab_search"
|
||||
android:layout_marginRight="16dp"
|
||||
android:layout_marginBottom="88dp"
|
||||
android:visibility="gone"/>
|
||||
<android.support.design.widget.FloatingActionButton
|
||||
android:id="@+id/fabTotpOverview"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="end|bottom|right"
|
||||
android:src="@drawable/ic_fab_totp"
|
||||
android:layout_marginRight="16dp"
|
||||
android:layout_marginBottom="160dp"
|
||||
android:visibility="gone"/>
|
||||
</android.support.design.widget.CoordinatorLayout>
|
||||
</RelativeLayout>
|
@@ -227,6 +227,7 @@
|
||||
<Compile Include="fileselect\FileSelectActivity.cs" />
|
||||
<Compile Include="fileselect\FileDbHelper.cs" />
|
||||
<Compile Include="search\SearchProvider.cs" />
|
||||
<Compile Include="search\SearchTotpResults.cs" />
|
||||
<Compile Include="SelectStorageLocationActivity.cs" />
|
||||
<Compile Include="services\AutofillBase\AutofillFieldMetadata.cs" />
|
||||
<Compile Include="services\AutofillBase\AutofillFieldMetadataCollection.cs" />
|
||||
@@ -1988,6 +1989,18 @@
|
||||
<ItemGroup>
|
||||
<AndroidResource Include="Resources\drawable-xhdpi\ic_entry_totp.png" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<AndroidResource Include="Resources\drawable-mdpi\ic_fab_search.png" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<AndroidResource Include="Resources\drawable-xhdpi\ic_fab_search.png" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<AndroidResource Include="Resources\drawable-mdpi\ic_fab_totp.png" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<AndroidResource Include="Resources\drawable-xhdpi\ic_fab_totp.png" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(MSBuildExtensionsPath)\Xamarin\Android\Xamarin.Android.CSharp.targets" />
|
||||
<!-- To modify your build process, add your task inside one of the targets below and uncomment it.
|
||||
Other similar extension points exist, see Microsoft.Common.targets.
|
||||
|
162
src/keepass2android/search/SearchTotpResults.cs
Normal file
162
src/keepass2android/search/SearchTotpResults.cs
Normal file
@@ -0,0 +1,162 @@
|
||||
/*
|
||||
This file is part of Keepass2Android, Copyright 2013 Philipp Crocoll. This file is based on Keepassdroid, Copyright Brian Pellin.
|
||||
|
||||
Keepass2Android is free software: you can redistribute it and/or modify
|
||||
it under the terms of the GNU General Public License as published by
|
||||
the Free Software Foundation, either version 3 of the License, or
|
||||
(at your option) any later version.
|
||||
|
||||
Keepass2Android is distributed in the hope that it will be useful,
|
||||
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
GNU General Public License for more details.
|
||||
|
||||
You should have received a copy of the GNU General Public License
|
||||
along with Keepass2Android. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
using System;
|
||||
using System.Linq;
|
||||
using System.Text.RegularExpressions;
|
||||
using Android.App;
|
||||
using Android.Content;
|
||||
using Android.Content.PM;
|
||||
using Android.OS;
|
||||
using Android.Preferences;
|
||||
using Android.Views;
|
||||
using Android.Widget;
|
||||
using keepass2android.view;
|
||||
using KeePassLib;
|
||||
|
||||
namespace keepass2android.search
|
||||
{
|
||||
/// <summary>
|
||||
/// Activity to show search results
|
||||
/// </summary>
|
||||
[Activity(Label = "@string/app_name", Theme = "@style/MyTheme_ActionBar", LaunchMode = Android.Content.PM.LaunchMode.SingleTop, ConfigurationChanges = ConfigChanges.Orientation | ConfigChanges.Keyboard | ConfigChanges.KeyboardHidden)]
|
||||
public class SearchTotpResults : GroupBaseActivity
|
||||
{
|
||||
|
||||
public static void Launch(Activity act, AppTask appTask, ActivityFlags? flags = null)
|
||||
{
|
||||
Intent i = new Intent(act, typeof(SearchTotpResults));
|
||||
|
||||
|
||||
if (flags != null)
|
||||
i.SetFlags((ActivityFlags)flags);
|
||||
|
||||
appTask.ToIntent(i);
|
||||
if (flags != null && (((ActivityFlags)flags) | ActivityFlags.ForwardResult) == ActivityFlags.ForwardResult)
|
||||
act.StartActivity(i);
|
||||
else
|
||||
act.StartActivityForResult(i, 0);
|
||||
}
|
||||
|
||||
public override bool MayPreviewTotp
|
||||
{
|
||||
get
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
protected override void OnCreate (Bundle bundle)
|
||||
{
|
||||
base.OnCreate (bundle);
|
||||
|
||||
if ( IsFinishing ) {
|
||||
return;
|
||||
}
|
||||
|
||||
SetResult(KeePass.ExitNormal);
|
||||
|
||||
// Likely the app has been killed exit the activity
|
||||
if (!App.Kp2a.DatabaseIsUnlocked)
|
||||
{
|
||||
Finish();
|
||||
}
|
||||
|
||||
Group = new PwGroup()
|
||||
{
|
||||
Name = GetString(Resource.String.TOTP)
|
||||
};
|
||||
try
|
||||
{
|
||||
foreach (var db in App.Kp2a.OpenDatabases)
|
||||
{
|
||||
foreach (var entry in db.EntriesById.Values)
|
||||
{
|
||||
var totpData = new Kp2aTotp().TryGetTotpData(new PwEntryOutput(entry, db));
|
||||
if (totpData?.IsTotpEntry == true)
|
||||
Group.AddEntry(entry, false);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
catch (Exception e)
|
||||
{
|
||||
Kp2aLog.LogUnexpectedError(e);
|
||||
Toast.MakeText(this, e.Message, ToastLength.Long).Show();
|
||||
Finish();
|
||||
return;
|
||||
}
|
||||
|
||||
if (Group == null || (!Group.Entries.Any()))
|
||||
{
|
||||
SetContentView(Resource.Layout.group_empty);
|
||||
}
|
||||
|
||||
SetGroupTitle();
|
||||
|
||||
FragmentManager.FindFragmentById<GroupListFragment>(Resource.Id.list_fragment).ListAdapter = new PwGroupListAdapter(this, Group);
|
||||
|
||||
}
|
||||
|
||||
public override bool EntriesBelongToCurrentDatabaseOnly
|
||||
{
|
||||
get { return false; }
|
||||
}
|
||||
|
||||
public override ElementAndDatabaseId FullGroupId
|
||||
{
|
||||
get { return null; }
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
public override void OnCreateContextMenu(IContextMenu menu, View v,
|
||||
IContextMenuContextMenuInfo menuInfo)
|
||||
{
|
||||
|
||||
AdapterView.AdapterContextMenuInfo acmi = (AdapterView.AdapterContextMenuInfo) menuInfo;
|
||||
ClickView cv = (ClickView) acmi.TargetView;
|
||||
cv.OnCreateMenu(menu, menuInfo);
|
||||
}
|
||||
|
||||
public override bool OnContextItemSelected(IMenuItem item) {
|
||||
AdapterView.AdapterContextMenuInfo acmi = (AdapterView.AdapterContextMenuInfo)item.MenuInfo;
|
||||
ClickView cv = (ClickView) acmi.TargetView;
|
||||
|
||||
bool result;
|
||||
|
||||
return cv.OnContextItemSelected(item);
|
||||
}
|
||||
|
||||
|
||||
public override bool OnSearchRequested()
|
||||
{
|
||||
Intent i = new Intent(this, typeof(SearchActivity));
|
||||
this.AppTask.ToIntent(i);
|
||||
i.SetFlags(ActivityFlags.ForwardResult);
|
||||
StartActivity(i);
|
||||
return true;
|
||||
}
|
||||
|
||||
public override bool IsSearchResult
|
||||
{
|
||||
get { return true; }
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -26,6 +26,10 @@ using Android.Text;
|
||||
using Android.Text.Style;
|
||||
using Android.Preferences;
|
||||
using KeePass.Util.Spr;
|
||||
using KeeTrayTOTP.Libraries;
|
||||
using PluginTOTP;
|
||||
using Android.Content;
|
||||
using System.ComponentModel;
|
||||
|
||||
|
||||
namespace keepass2android.view
|
||||
@@ -37,8 +41,11 @@ namespace keepass2android.view
|
||||
private readonly TextView _textView;
|
||||
private readonly TextView _textviewDetails;
|
||||
private readonly TextView _textgroupFullPath;
|
||||
private readonly ProgressBar _totpCountdown;
|
||||
private readonly TextView _totpText;
|
||||
private readonly LinearLayout _totpLayout;
|
||||
|
||||
private int _pos;
|
||||
private int _pos;
|
||||
|
||||
private int? _defaultTextColor;
|
||||
|
||||
@@ -82,7 +89,18 @@ namespace keepass2android.view
|
||||
_textgroupFullPath = (TextView)ev.FindViewById(Resource.Id.group_detail);
|
||||
_textgroupFullPath.TextSize = PrefsUtil.GetListDetailTextSize(groupActivity);
|
||||
|
||||
_showDetail = PreferenceManager.GetDefaultSharedPreferences(groupActivity).GetBoolean(
|
||||
_totpCountdown = ev.FindViewById<ProgressBar>(Resource.Id.TotpCountdownProgressBar);
|
||||
_totpText = ev.FindViewById<TextView>(Resource.Id.totp_text);
|
||||
_totpLayout = ev.FindViewById<LinearLayout>(Resource.Id.totp_layout);
|
||||
|
||||
_totpLayout.LongClick += (sender, args) =>
|
||||
{
|
||||
string totp = UpdateTotp();
|
||||
if (!String.IsNullOrEmpty(totp))
|
||||
CopyToClipboardService.CopyValueToClipboardWithTimeout(_groupActivity, totp, true);
|
||||
};
|
||||
|
||||
_showDetail = PreferenceManager.GetDefaultSharedPreferences(groupActivity).GetBoolean(
|
||||
groupActivity.GetString(Resource.String.ShowUsernameInList_key),
|
||||
Resources.GetBoolean(Resource.Boolean.ShowUsernameInList_default));
|
||||
|
||||
@@ -112,20 +130,20 @@ namespace keepass2android.view
|
||||
ev.FindViewById(Resource.Id.icon).Visibility = ViewStates.Visible;
|
||||
ev.FindViewById(Resource.Id.check_mark).Visibility = ViewStates.Invisible;
|
||||
|
||||
Database db = App.Kp2a.FindDatabaseForElement(_entry);
|
||||
_db = App.Kp2a.FindDatabaseForElement(_entry);
|
||||
|
||||
ImageView iv = (ImageView)ev.FindViewById(Resource.Id.icon);
|
||||
bool isExpired = pw.Expires && pw.ExpiryTime < DateTime.Now;
|
||||
if (isExpired)
|
||||
{
|
||||
db.DrawableFactory.AssignDrawableTo(iv, Context, db.KpDatabase, PwIcon.Expired, PwUuid.Zero, false);
|
||||
_db.DrawableFactory.AssignDrawableTo(iv, Context, _db.KpDatabase, PwIcon.Expired, PwUuid.Zero, false);
|
||||
} else
|
||||
{
|
||||
db.DrawableFactory.AssignDrawableTo(iv, Context, db.KpDatabase, pw.IconId, pw.CustomIconUuid, false);
|
||||
_db.DrawableFactory.AssignDrawableTo(iv, Context, _db.KpDatabase, pw.IconId, pw.CustomIconUuid, false);
|
||||
}
|
||||
|
||||
String title = pw.Strings.ReadSafe(PwDefs.TitleField);
|
||||
title = SprEngine.Compile(title, new SprContext(_entry, db.KpDatabase, SprCompileFlags.All));
|
||||
title = SprEngine.Compile(title, new SprContext(_entry, _db.KpDatabase, SprCompileFlags.All));
|
||||
var str = new SpannableString(title);
|
||||
|
||||
if (isExpired)
|
||||
@@ -146,7 +164,7 @@ namespace keepass2android.view
|
||||
_textView.SetTextColor(new Color((int)_defaultTextColor));
|
||||
|
||||
String detail = pw.Strings.ReadSafe(PwDefs.UserNameField);
|
||||
detail = SprEngine.Compile(detail, new SprContext(_entry, db.KpDatabase, SprCompileFlags.All));
|
||||
detail = SprEngine.Compile(detail, new SprContext(_entry, _db.KpDatabase, SprCompileFlags.All));
|
||||
|
||||
if ((_showDetail == false) || (String.IsNullOrEmpty(detail)))
|
||||
{
|
||||
@@ -173,7 +191,7 @@ namespace keepass2android.view
|
||||
String groupDetail = pw.ParentGroup.GetFullPath();
|
||||
if (App.Kp2a.OpenDatabases.Count() > 1)
|
||||
{
|
||||
groupDetail += "(" + App.Kp2a.GetFileStorage(db.Ioc).GetDisplayName(db.Ioc) + ")";
|
||||
groupDetail += "(" + App.Kp2a.GetFileStorage(_db.Ioc).GetDisplayName(_db.Ioc) + ")";
|
||||
}
|
||||
|
||||
var strGroupDetail = new SpannableString (groupDetail);
|
||||
@@ -186,7 +204,16 @@ namespace keepass2android.view
|
||||
_textgroupFullPath.Visibility = ViewStates.Visible;
|
||||
}
|
||||
|
||||
}
|
||||
//try to get totp data
|
||||
UpdateTotp();
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
public void ConvertView(PwEntry pw, int pos)
|
||||
{
|
||||
@@ -248,6 +275,42 @@ namespace keepass2android.view
|
||||
{
|
||||
LaunchEntry();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
private TotpData _totpData;
|
||||
|
||||
private Database _db;
|
||||
|
||||
public string UpdateTotp()
|
||||
{
|
||||
ISharedPreferences prefs = PreferenceManager.GetDefaultSharedPreferences(_groupActivity);
|
||||
bool showTotpDefault = _groupActivity.MayPreviewTotp;
|
||||
|
||||
|
||||
if (showTotpDefault)
|
||||
_totpData = new Kp2aTotp().TryGetTotpData(new PwEntryOutput(_entry, _db));
|
||||
else
|
||||
_totpData = null;
|
||||
|
||||
if (_totpData?.IsTotpEntry != true)
|
||||
{
|
||||
_totpLayout.Visibility = ViewStates.Gone;
|
||||
return null;
|
||||
}
|
||||
|
||||
_totpLayout.Visibility = ViewStates.Visible;
|
||||
|
||||
TOTPProvider prov = new TOTPProvider(_totpData);
|
||||
string totp = prov.GenerateByByte(_totpData.TotpSecret);
|
||||
|
||||
_totpText.Text = totp;
|
||||
var progressBar = _totpCountdown;
|
||||
progressBar.Progress = prov.Timer;
|
||||
progressBar.Max = prov.Duration;
|
||||
|
||||
return totp;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
Reference in New Issue
Block a user