Compare commits

...

122 Commits

Author SHA1 Message Date
a31abf0974 3.2.0 rc1 release (#709)
prepare 3.2.0 rc1 release

RC1 release of 3.2.0

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/709
2020-09-26 20:51:12 +02:00
6d466e2542 Crowdin 2020-09-26 (#711)
Crowdin Update

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/711
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-09-26 20:50:15 +02:00
01bd61ad8e Fixing CI (#710)
Fixing CI.

Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/710
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-09-26 20:21:29 +02:00
4031c32fc8 Introduce Pro version for play store (#708)
Introduce Pro version for play store

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/708
2020-09-26 17:05:51 +02:00
d51d2d5164 Android 11 support (#707)
update libs

Android 11 support

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/707
2020-09-26 15:55:30 +02:00
7b8bc21a83 Adjust logo with new colors (#706)
Adjust logo with new colors

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/706
2020-09-26 09:18:41 +02:00
1c1f73eafc Redo About screen UI and some refactors (#705)
Redo About screen UI and some refactors

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/705
2020-09-26 07:54:31 +02:00
02672aef3d Refactor: remove instanceUrlWithProtocol (#698)
Refactor: remove instanceUrlWithProtocol

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/698
2020-09-24 18:53:28 +02:00
23fb1ce71f Create PR (#689)
Merge branch 'master' into create-pr

consistent button height

implement create pr

Merge branch 'master' into create-pr

Remove save button for labels

minor improvements

new line

Implement interfaces for labels data

UI updates to labels dialog

Merge branch 'master' into create-pr

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Add labels list

Add ui elements, api calls for branches and milestone

Add activity, layout, click trigger and checks

Merge branch 'master' into create-pr

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Add bs item

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

endline

Co-authored-by: 6543 <6543@noreply.codeberg.org>
Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/689
2020-09-24 18:51:20 +02:00
1f5eeb5632 Notification badge in navigation menu (#702)
Merge branch 'master' into 700-notifications-counter

Notification badge in navigation menu

Co-authored-by: 6543 <6543@noreply.codeberg.org>
Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/702
2020-09-18 06:51:41 +02:00
78782d159a UI improvements (#699)
UI improvements

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/699
2020-09-16 20:03:52 +02:00
a75ffe0381 Transfer repository ownership (#696)
simplify comments

Transfer repository ownership

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/696
2020-09-16 08:53:13 +02:00
c4279dcd77 Improve crash report notification string (#697)
Improve crash report notification string

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/697
2020-09-16 08:52:32 +02:00
14b1256ce1 Crowdin 2020-09-13 (#694)
Add Czech

Update 2020-09-13

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/694
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-09-13 13:11:55 +02:00
7b72815bcb Add account new UI (#692)
Merge branch 'new-account-ui' of codeberg.org:gitnex/GitNex into new-account-ui

Merge branch 'master' into new-account-ui

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Merge branch 'master' into new-account-ui

Transition of adding account to new UI

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

endline

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/692
2020-09-13 06:57:04 +02:00
5e6c600e71 Repo settings (delete-edit) (#683)
better var names

remove migration

Merge branch 'repo-settings-delete-migrate-edit' of codeberg.org:gitnex/GitNex into repo-settings-delete-migrate-edit

delete repository

Merge branch 'master' into repo-settings-delete-migrate-edit

Can edit repo properties now

Add progress indicator, call for save

Pull repo info into dialog

Repo properties in custom dialog

settings activity with labels

Merge branch 'master' into repo-settings-delete-migrate-edit

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

add bottom sheet entry

endline

Co-authored-by: M M Arif <mmarif@swatian.com>
Co-authored-by: 6543 <6543@noreply.codeberg.org>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/683
2020-09-13 06:54:05 +02:00
dbf5be25a5 Add stat indicator pr/issues (#686)
Merge branch 'master' into add-stat-indicator

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Show PR/Issue stat

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

endline

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/686
2020-09-13 06:52:30 +02:00
2bfe0b8d1a Fix create issue crash on label added and removed (#685)
Merge branch 'master' into fix-create-issue-crash

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Fix crash when label added and removed

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

endline

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/685
2020-09-13 06:50:06 +02:00
0c92eb3fa2 Fix active account selector (#687)
Merge branch 'master' into fix-active-account-selector

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Fix active account selector

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

endline

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/687
2020-09-13 06:48:30 +02:00
32f3080283 Fix fragments when view forks from repo info (#688)
Temp fix fragments forks

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

Merge branch 'master' of codeberg.org:gitnex/GitNex into master

endline

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/688
2020-09-13 06:37:10 +02:00
7342668a1b Fixing gitlab ci releases (#690)
Fixing gitlab ci releases.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/690
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-09-08 20:44:12 +02:00
6f9bbe4c58 Optimizing user accounts list. (#684)
Optimizing user accounts list.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/684
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-09-07 16:29:04 +02:00
b2b42887f7 Move branch commits to files popup (#682)
Move commits to file sub menu

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/682
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-09-05 15:43:29 +02:00
37f622b952 Update libs (#681)
Update libs

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/681
2020-09-04 16:33:59 +02:00
d677c90b01 helper Version: add valid() function (#670)
Merge branch 'master' into VersionValid

format code

introduce Version.valid()

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/670
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-09-04 16:33:37 +02:00
23d3ba7f42 Fix crash on token logins with Require signin view enabled (#678)
Fix crash on token logins with Require signin view enabled

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/678
2020-09-03 19:26:24 +02:00
a42d888eb7 Share only stack trace (#675)
Share only stack trace

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/675
2020-09-03 18:12:53 +02:00
bbcffd67d6 Crowdin 2020-08-28 (#668)
Crowdin 2020-08-28

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/668
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-09-02 21:08:23 +02:00
00eb9c9135 Fix edit comment draft (#661)
Fix edit comment draft

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/661
2020-08-24 12:03:16 +02:00
28a23d30f8 Fix crash on login (#662)
Fix crash on login

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/662
2020-08-24 12:02:45 +02:00
82f874dc37 Official start of 3.2 development (#660)
Official start of 3.2 development

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/660
2020-08-21 20:19:44 +02:00
b60a0e7a92 3.1.0 release (#659)
3.1.0 release

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/659
2020-08-21 18:32:56 +02:00
185bdb863d Crowdin 2020-08-21 (#658)
Crowdin 2020-08-21

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/658
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-08-21 18:20:28 +02:00
da338fcc83 Fix styling radio buttons (#657)
Fix styling radio buttons

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/657
2020-08-21 16:59:54 +02:00
6d8a87358d Copy comment url to clipboard (#655)
Copy comment url to clipboard

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/655
2020-08-21 16:17:48 +02:00
5fc6cdde63 New Retro theme (#654)
New Retro theme

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/654
2020-08-20 18:21:55 +02:00
dc6b1bb5b6 Release 3.1.0 RC2 (#653)
Release 3.1.0 RC2

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/653
2020-08-19 09:07:12 +02:00
8768c87b8a Update missing progress bars (#652)
update missing progress bars

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/652
2020-08-18 19:55:34 +02:00
7caff70946 Edit and delete a file (#626)
update if file is modified on resume

implementation of edit file

Merge branch 'master' into 44-delete-file

Merge branch '44-delete-file' of codeberg.org:gitnex/GitNex into 44-delete-file

Merge branch 'master' into 44-delete-file

# Conflicts:
#	app/src/main/java/org/mian/gitnex/activities/CreateFileActivity.java
#	app/src/main/java/org/mian/gitnex/activities/FileViewActivity.java
#	app/src/main/java/org/mian/gitnex/activities/RepoDetailActivity.java
#	app/src/main/java/org/mian/gitnex/fragments/BottomSheetFileViewerFragment.java

Merge branch 'master' into 44-delete-file

implement delete file

add links to bottomsheet

Co-authored-by: M M Arif <mmarif@swatian.com>
Co-authored-by: 6543 <6543@noreply.codeberg.org>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/626
2020-08-18 16:37:10 +02:00
76137c56bc Improve drafts ui, add edited comments, create new ones on each call (#628)
Merge branch 'master' into 627-save-edit-draft

# Conflicts:
#	app/src/main/java/org/mian/gitnex/actions/IssueActions.java

Merge branch 'master' into 627-save-edit-draft

Improve drafts, add edited comments, create new ones on each call.

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/628
2020-08-18 16:11:31 +02:00
dcacf1f141 Design Accounts from Nav menu (#648)
Merge branch 'master' into new-account-design

Merge branch 'master' into new-account-design

enhance the dialog UI

Merge branch 'master' into new-account-design

New account design in nav with dialog popup list

New design for accounts accessing

Co-authored-by: 6543 <6543@noreply.codeberg.org>
Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/648
2020-08-18 16:10:46 +02:00
7585eb4834 Update bug icon (#651)
update bug icon

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/651
2020-08-17 19:08:29 +02:00
7dd231ee95 Set notifications as home srceen (#644) 2020-08-12 09:31:39 +02:00
d5fd6d8cc4 Fix share issue url (#643) 2020-08-12 09:31:06 +02:00
28963bb079 Using language instead of country. (#647)
Using language instead of country.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/647
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-08-11 18:32:30 +02:00
87649ebae8 Introduce new progress indicators (#638)
Add indicator to the rest of fragments/activities

Merge branch 'master' into profress-indicators

# Conflicts:
#	app/src/main/res/layout/activity_credits.xml
#	app/src/main/res/layout/activity_sponsors.xml

wip to remove old indicator

Make dark green as primary color, clean up app files

Introduce new progress indicators

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/638
2020-08-09 10:23:51 +02:00
a92969a47f Fix jumps in drawer when open for all items(icons, user data) (#639)
Fix drawer jumps when open for all items

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/639
2020-08-09 10:23:19 +02:00
d9cd04facf Layout improvements (#637)
Layout improvements

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/637
2020-08-08 17:43:14 +02:00
3eacfe91fe 3.1.0 RC1 release (#636)
3.1.0 RC1 release

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/636
2020-08-07 17:28:39 +02:00
e38d141d38 Quick labels, assignes dialog ui fixes (#635)
labels, assignes dialog ui fixes

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/635
2020-08-07 17:23:04 +02:00
7c40c049d4 Fix email login loop (can login with email again) (#629)
Merge branch 'master' into fix-email-logins

# Conflicts:
#	app/src/main/java/org/mian/gitnex/activities/LoginActivity.java

cleanup

Fix emails logins loop

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/629
2020-08-06 17:31:31 +02:00
b4b7981722 Open respective content when tap on repo info prs, watchers, forks, stargazers (#632)
Merge branch 'master' into open-repo-info-item

Open respective content when tap on repo info items, prs, watchers, forks, stargazers

Co-authored-by: 6543 <6543@noreply.codeberg.org>
Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/632
2020-08-06 17:19:37 +02:00
96fad2d73e Copy urls (#631)
fix url open in browser

Copy org and repo url

Copy urls

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/631
2020-08-06 17:18:02 +02:00
24064192e4 Enhance dialog buttons (#633)
switch to outline buttons

Enhance and fix color scheme for dialogs

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/633
2020-08-06 17:17:27 +02:00
12a7b6040b App wide UI changes and refactors (#630)
Enhance and update the buttons across the app, colorful animation on tap

update toasty in view models

update toasty in fragments

update toasty in actions, activities, adapters

Alert dialogs buttons arrangements

strings fixes

switch to fab buttons

remove snackbar

Enhance whole app UI, bring consistency among the elements

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/630
2020-08-06 17:16:51 +02:00
30921ea330 Multiple accounts support (#624)
Title update

Color clean up

switch to another account and update the token at login

Add new account

Add fab button for new account and activity

update libs

Remove account from Manage accounts list

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/624
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-08-04 22:50:04 +02:00
ea36a3f6d6 Repository forks (#606)
Repository forks

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/606
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-29 21:46:58 +02:00
f1ecc42876 Md support in file viewer (#607)
format

implement support for md on tap on icon

show icon for md files only

Add md to top bar

Co-authored-by: 6543 <6543@obermui.de>
Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/607
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-29 20:45:05 +02:00
73e7acfbdf Drop support for login with email (#622)
Drop support for login with email

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/622
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-29 20:28:24 +02:00
a9ad91d954 Fix drafts from notifications view (#618)
Fix drafts when coming from notifications

Fix star/watchers layout

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/618
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-29 20:04:40 +02:00
ff537b79ff BasicAuth Login: Handle existing token (#611)
fix code comment

bugfix

code format

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/611
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-29 16:27:47 +02:00
7efc8650fa Remove unlock for public repos (#605)
Remove unlock for public repos

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/605
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-26 12:01:15 +02:00
a171abc0b8 Official start of 3.1.0 development (#603)
Official start of 3.1.0 development

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/603
2020-07-23 20:17:38 +02:00
0928e936d7 Prepare release (#599)
update  feature list in readme

Merge branch 'master' into 480-update-screenshots

update desc for f-droid

update screenshots, add changelogs

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/599
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-23 19:35:46 +02:00
a29011c6a2 Crowdin 2020-07-23 (#602)
Crowdin Update

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/602
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-23 18:38:18 +02:00
c09fc4988a Support Samsung DeX (#601)
Support Samsung DeX

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/601
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-23 18:37:32 +02:00
39ac49b258 Notifications (#554)
Cleanup

Extending and improving notifications

Using new icons instead

Lowering polling delay to one minute and other improvements

Fixing minor issues

Simplifying progress layout

Fixing bugs and other improvements

Adding translations

Notifications

Co-authored-by: opyale <opyale@noreply.gitea.io>
Co-authored-by: 6543 <6543@noreply.codeberg.org>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/554
Reviewed-by: 6543 <6543@noreply.codeberg.org>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-22 21:32:42 +02:00
cd55f946f0 Crowdin 2020-07-22 (#597)
Crowdin Update

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/597
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-07-22 14:48:12 +02:00
b529f81115 Fix some bugs (#596)
remove redundant casting

Fix edittext layout when typing(reduce size), fix refresh drafts. Minor improvements

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/596
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-19 15:44:08 +02:00
e6109ef36d Search drafts (#574)
Merge branch 'master' into search-drafts

Merge branch 'master' into search-drafts

Merge branch 'master' into search-drafts

Merge branch 'master' into search-drafts

Merge branch 'master' into search-drafts

Merge branch 'master' into search-drafts

Merge branch 'master' into search-drafts

Merge branch 'master' into search-drafts

Merge branch 'master' into search-drafts

# Conflicts:
#	app/src/main/java/org/mian/gitnex/fragments/DraftsFragment.java

search drafts

Co-authored-by: 6543 <6543@noreply.codeberg.org>
Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/574
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-19 12:33:58 +02:00
e00fcd846a Add missed icons and improve the ratio of all icons across the app (#592)
Merge branch 'master' into new-missing-icons

Merge branch 'master' into new-missing-icons

Fix background and icon

Fix search bar icons and layout to match the themes

new lines?

Merge branch 'master' into new-missing-icons

Add missed icons, and improve the ratio of all icons across the app

Co-authored-by: 6543 <6543@noreply.codeberg.org>
Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/592
2020-07-19 12:24:47 +02:00
060c86c090 Add server avatar to user accounts (#594)
Add server avatar to user accounts

Co-authored-by: 6543 <6543@noreply.codeberg.org>
Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/594
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-19 12:13:37 +02:00
26f54280a1 Add explore and drafts to set as home screen options (#588)
Fix icon cut off sizes

Add explore and drafts to set as home screen options

Co-authored-by: 6543 <6543@noreply.codeberg.org>
Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/588
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-19 12:05:08 +02:00
8a7923cba7 Fix VersionCheck (#591)
code dedub

Bugfix & Test Correction

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/591
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-07-14 18:20:00 +02:00
673b9f564c Crowdin 2020-07-14 (#590)
crowdin_2020-07-14

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/590
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-14 17:14:06 +02:00
d1be03956c Transition of old icons to new ones (#589)
last set of updates and changes to the icons

Add more icons

WIP : transition of more icons

Switch of icons to new icons for the whole app - WIP

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/589
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-12 19:18:50 +02:00
caa437d5e3 Switch branches (#571)
Fix default branch

Merge branch 'master' into switch-branches

# Conflicts:
#	app/src/main/res/layout/bottom_sheet_repo.xml
#	app/src/main/res/values/strings.xml

update icon

Merge branch 'master' into switch-branches

Merge branch 'master' into switch-branches

update the missing parts

Minor updates

Merge branch 'master' into switch-branches

Merge branch 'master' into switch-branches

# Conflicts:
#	app/src/main/java/org/mian/gitnex/activities/CreateIssueActivity.java
#	app/src/main/java/org/mian/gitnex/activities/RepoDetailActivity.java
#	app/src/main/java/org/mian/gitnex/fragments/BottomSheetRepoFragment.java
#	app/src/main/java/org/mian/gitnex/fragments/FilesFragment.java

Add branch to breadcrumb and dir structure fix

Make change branch work

clean up

Merge branch 'master' into switch-branches

add icon in top bar, add interface listener

Merge branch 'master' into switch-branches

Merge remote-tracking branch 'remotes/main/master' into switch-branches

# Conflicts:
#	app/src/main/java/org/mian/gitnex/activities/LoginActivity.java
#	app/src/main/java/org/mian/gitnex/fragments/ProfileFragment.java
#	app/src/main/java/org/mian/gitnex/helpers/PathsHelper.java

Switching between branches.

Minor fixes

Merge remote-tracking branch 'remotes/main/master' into login-fix

URL parsing, label and other improvements.

Co-authored-by: M M Arif <mmarif@swatian.com>
Co-authored-by: 6543 <6543@noreply.codeberg.org>
Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/571
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-12 17:14:50 +02:00
25036ce5d2 Remove Unused Locales (#585)
Remove Unused Locales

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/585
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-11 12:49:35 +02:00
a8a34ccc7a New icons (#587)
repo info icons update

Update icons across the app

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/587
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-07-10 22:54:09 +02:00
f87e8020d8 Remove Unused Resources (#586)
Remove Unused Resources

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/586
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-10 12:43:51 +02:00
4d67e63db4 Fix license (#584)
Fix license

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/584
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-07-09 17:42:13 +02:00
3561dde19f Badges and drone fix. (#583)
Removing link

Badges and drone fix.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/583
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-09 15:18:21 +02:00
9c48dec54d Delete drafts [settings] (#576)
Merge branch '450-drafts-settings' of codeberg.org:gitnex/GitNex into 450-drafts-settings

Fix package move

Merge branch 'master' into 450-drafts-settings

Merge branch 'master' into 450-drafts-settings

fix default value save

Delete drafts settings

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/576
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-07-09 13:55:09 +02:00
3d72d68e14 Fixing CI (#582)
Fixing CI

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/582
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-09 13:37:44 +02:00
47b24470e6 Improving CI. (#581)
Improving CI.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/581
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-09 13:29:36 +02:00
1db6a3294b Using GitLab CI. (#580)
Using smaller image and publishing releases.

Fixing things.

Merge branch 'gitlab-ci' of https://codeberg.org/opyale/GitNex into gitlab-ci

Removing eclint.

Merge branch 'master' into gitlab-ci

Only run jobs when master changed.

Using GitLab CI.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/580
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-09 08:55:05 +02:00
500dc019c1 Moving TinyDB and AppUtil to helpers. (#579)
Moving TinyDB and AppUtil to helpers.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/579
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-07-07 19:15:01 +02:00
e2aff890d7 Accounts overview screen (#577)
optimize url string

Overview of accounts in the app

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/577
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-07-07 16:20:43 +02:00
cdfc2cfb9e Implement drafts, introduce Room persistence library for db (#139)
Fix no draft message

translation updates

format improvements

typo update

some renaming refactors

Use better naming convention

remove duplicate source

arrange draft titles

enhance click listener area

Launch drafts from reply screen and clean up

Add message draft saved

update repositories tasks

Update user accounts repository with thread, remove async tasks

remove async task in drafts

update layout, change async to thread in drafts

Merge branch 'master' into pull_139

# Conflicts:
#	app/build.gradle
#	app/src/main/java/org/mian/gitnex/activities/LoginActivity.java

Merge branch 'master' into pull_139

# Conflicts:
#	app/src/main/java/org/mian/gitnex/activities/ReplyToIssueActivity.java

Merge branch 'pull_139' of codeberg.org:gitnex/GitNex into pull_139

# Conflicts:
#	app/src/main/java/org/mian/gitnex/adapters/MyReposListAdapter.java

Merge branch 'master' into pull_139

# Conflicts:
#	app/src/main/java/org/mian/gitnex/activities/LoginActivity.java
#	app/src/main/java/org/mian/gitnex/activities/ReplyToIssueActivity.java
#	app/src/main/java/org/mian/gitnex/adapters/MyReposListAdapter.java

Merge branch 'master' into pull_139

Merge branch 'master' into pull_139

Merge branch 'master' into pull_139 and fix conflicts

# Conflicts:
#	app/build.gradle
#	app/src/main/java/org/mian/gitnex/activities/LoginActivity.java
#	app/src/main/java/org/mian/gitnex/activities/MainActivity.java
#	app/src/main/java/org/mian/gitnex/activities/ReplyToIssueActivity.java
#	app/src/main/java/org/mian/gitnex/adapters/MyReposListAdapter.java
#	app/src/main/java/org/mian/gitnex/helpers/StaticGlobalVariables.java
#	app/src/main/res/values/strings.xml

Code Format

Merge branch 'master' into 15-comments-draft

Merge branch 'master' into 15-comments-draft

Merge branch 'master' into 15-comments-draft

# Conflicts:
#	app/src/main/java/org/mian/gitnex/activities/MainActivity.java
#	app/src/main/res/values/strings.xml

Go to draft, save on type and other fixes

delete all drafts, added messages where needed

delete draft

Force logout

Merge branch 'master' into 15-comments-draft

Merge branch 'master' into 15-comments-draft

# Conflicts:
#	app/src/main/java/org/mian/gitnex/activities/MainActivity.java
#	app/src/main/java/org/mian/gitnex/helpers/StaticGlobalVariables.java

check if account data is null, we need to log the user out for the 1st time.

Merge branch 'master' into 15-comments-draft

fix repo owner, name sequence

Add comments for test, show drafts list

Add repos to db

Add account to db and other refactors to the code

Merge branch 'master' into 15-comments-draft

Merge branch 'master' into 15-comments-draft

Merge branch 'master' into 15-comments-draft

Merge branch 'master' into 15-comments-draft

# Conflicts:
#	app/build.gradle
#	app/src/main/AndroidManifest.xml

Merge branch 'master' into 15-comments-draft

merge

more queries, added dao repositories, layout update

Added queries in dao

some refactor. added models, dao, entities (accounts, repositories, drafts)

WIP on implementing drafts, introduced Room persistence library for db.

Co-authored-by: M M Arif <mmarif@swatian.com>
Co-authored-by: 6543 <6543@obermui.de>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/139
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-07-04 22:51:55 +02:00
f135508745 Release 3.0.0 rc3 (#570)
Release 3.0.0 rc3

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/570
2020-06-30 21:08:10 +02:00
3e5e94790e Update libs, remove depricated libs (#566)
proper decleration

Merge branch 'update-libs-fix-deps' of codeberg.org:gitnex/GitNex into update-libs-fix-deps

import searchview and other improvements

Merge branch 'master' into update-libs-fix-deps

Update libs, remove depricated libs

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/566
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-06-30 20:59:11 +02:00
62aace4b91 Fix old URLs which do not have a slash at the end. (#568)
Merge branch 'master' into fix-older-urls

Fix old URLs which do not have a slash at the end.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/568
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-30 20:36:24 +02:00
2412245a9f Fixing path issues. (#567)
Fixing path issues.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/567
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-30 20:19:55 +02:00
e872069093 Proper URL parsing, label redesign and other improvements. (#564)
Final improvements.

Fixing reply mention.

Do NOT use "instanceUrlRaw" as of now.

Minor fixes

Merge remote-tracking branch 'remotes/main/master' into login-fix

URL parsing, label and other improvements.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/564
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-30 16:43:27 +02:00
5672208fd0 Adding ability to quote and to copy issue comments. (#562)
Minor fix.

Merge branch 'master' into reply-tools

Merge remote-tracking branch 'opyale/reply-tools' into reply-tools

Changing names.

Merge branch 'master' into reply-tools

Adding ability to cite and to copy issue comments.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Co-authored-by: 6543 <6543@noreply.codeberg.org>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/562
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-28 19:26:59 +02:00
7379e9945d Fixing bugs of previous pull (#563)
Fixing bugs of previous pull.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/563
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-06-28 18:48:33 +02:00
815417bf11 Refactoring LoginActivity and other improvements. (#561)
Adding error message for login().

Final touch.

Refactoring LoginActivity and other improvements.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/561
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-06-28 17:11:59 +02:00
95fc5e1e9a Fix bug #549, add more file ext to file viewer (#560)
Fix empty release notes bug

Add new sponsor

Fix bug #549, add more file ext to file viewer

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://codeberg.org/gitnex/GitNex/pulls/560
Reviewed-by: opyale <opyale@noreply.codeberg.org>
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-06-28 16:45:39 +02:00
f285d47a0b Fix Crash on closed PRs with deleted Fork (#559)
Fix edge-case DeletedFork of a Pull-Branch

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-26 17:09:18 +02:00
2483968f11 Inverting color of divider too (#553)
Inverting color of divider too

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-06-25 01:27:13 +02:00
d0fde4e791 Adjusting icon color to fit background. (#551)
Adjusting icon color to fit background.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-24 23:02:22 +02:00
c7c2ac2a11 Enhance bottomsheets ui (#550)
Fix name collision in themes

Add space between org and repo name

standard use of dimens

more ui improvements

wip to enhance all bottom sheets

Fix radius and improve the ui

enhance bottom sheet

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-06-24 22:29:58 +02:00
4f79ea0156 Fix Crash when searching issues/pr (#547)
fix in pr and ms fragments

Fix Crash when searching issues/pr

Co-authored-by: M M Arif <mmarif@swatian.com>
Co-authored-by: 6543 <6543@obermui.de>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-24 17:05:02 +02:00
22943ca9cd Fix user team search crash (#545)
Fix team user search crash

Refactor userName

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-06-23 20:59:23 +02:00
5a10127c1c Calculate ImageContrastColor more precise & some doc nits (#544)
Fixing color bug, updating license headers and CONTRIBUTORS

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-by: 6543 <6543@noreply.codeberg.org>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-23 16:54:27 +02:00
7de29687eb Fixing collaborators bug and some improvements in RepoDetailActivity (#543)
* Minor improvements.

* Fixing collaborators bug and many (performance) improvements in RepoDetailActivity.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-06-22 18:28:08 +02:00
1a95475140 Gitea >= v1.12.0 only need read rights for Colaborators Tab (#542)
show "Add Collaborator" option only if you have the right to do so

gitea >= v1.12.0 only need read rights for Colaborators Tab

Signed-off-by: 6543 <6543@obermui.de>

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-22 17:59:36 +02:00
d2265aecae Fix profile title (#541)
Fix profile
2020-06-22 09:57:21 +02:00
626746be8b Release 3.0.0 rc2 (#539)
release 3.0.0 rc2

Co-authored-by: M M Arif <mmarif@swatian.com>
2020-06-11 15:47:28 +02:00
f21f23c1f0 Refactor FileDiffActivety (#537)
use androidx @NonNull instead of jetbrains @NotNull

Merge branch 'master' into refactor_FileDiffActivity

code format corrections

Merge branch 'master' into refactor_FileDiffActivity

add Unit TESTs for ParseDiff.getFileDiffViewArray

add get methods

make rm/add similar to gitea stats

calc diff stat based on diff itself

rename getFileContents -> toString

fix empty content bug & add comments

format AppUtil.java

rm unused

working version

skip binary files for now ... [DONT CRASH]

better regex

format FileDiffView.java

rename toolbar_title -> toolbarTitle

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-11 15:31:11 +02:00
5005fcc5b5 Redesign releases screen (#526)
Add download assets

implement release layout in adapter

update the layout

Fixing gravity.

Adding layouts for new release items.

Co-authored-by: M M Arif <mmarif@swatian.com>
Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-06-11 01:45:11 +02:00
008e446b93 GitNex drop 1.10 support and add 1.13 (#538)
GitNex drop 1.10 support and add 1.13

rm unused

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-10 17:22:49 +02:00
50e0142f6c Pull Diff View: Use new API if gitea >= 1.13.0 (#536)
right arg order & right instanceUrl

use new API if gitea >= 1.13.0

correct name

format code

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-06-09 15:36:08 +02:00
42640f2d1c Updating gradle. (#535)
Updating gradle.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-08 18:43:57 +02:00
4a8ee2ea96 Improving design of organisation detail page. (#534)
Design changes and updating dependencies.

Small fix.

Adding missing library.

Cleanup.

Improving design of organisation detail page.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-08 08:34:53 +02:00
acc55e3433 Using blurred avatar as background. (#532)
Fixing NullPointerException when image isn't loaded yet.

Display country instead of raw language code.

Minor improvements and contrasting color.

First changes.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-06 22:04:07 +02:00
e267aa5100 Show archived repo message (#530)
Implement archived repo in all adapters

Merge branch 'archive-repo2' into archive-repo

Fix typos

Fixing gravity.

Restoring old names.

Design changes.

Adjusting sizing.

Improving design of archived message.

Show archived repo message and other fixes

Co-authored-by: M M Arif <mmarif@swatian.com>
Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-by: opyale <opyale@noreply.codeberg.org>
2020-06-06 21:41:19 +02:00
5e41469452 Move to CodeBerg (#528)
the rest

move to CodeBerg

Co-authored-by: 6543 <6543@obermui.de>
Reviewed-by: M M Arif <mmarif@noreply.codeberg.org>
2020-06-04 17:37:51 +02:00
55473701b8 Improving design of "Show more information" (#527)
Adding comments to editorconfig.

Formatting.

Adding link color attribute.

Minor improvements.

Use dedicated layout for additional information.

Co-authored-by: opyale <opyale@noreply.gitea.io>
Reviewed-by: 6543 <6543@noreply.codeberg.org>
2020-06-04 16:21:23 +02:00
546346ff48 Improving milestones. (#525)
Removing unused strings.

Adding a little bit more space between title and progress bar.

Swapping icons.

Merge remote-tracking branch 'remotes/main/master' into improve-milestones

# Conflicts:
#	app/src/main/res/layout/list_milestones.xml

Minor improvements.

Merge branch 'improve-layouts' of https://gitea.com/opyale/GitNex into improve-milestones

Merge branch 'improve-layouts' of https://gitea.com/gitnex/GitNex into improve-milestones

Moving items.

Merge branch 'master' into improve-layouts

Merge branch 'master' into improve-layouts

Translation and additional formatting.

Enhancing editorconfig

Formatting and removing unused imports.

Removing milestone state.

Improving milestones.

branches and milestones layout update. Fix milestone infinite pagination loop for lower versions

layout updates for issues, pr. Fix pr nullable objects for lower versions

improve files layout

improve org info and list orgs

improve teams list layout by org

Fix repo layouts

Co-authored-by: M M Arif <mmarif@swatian.com>
Reviewed-on: https://gitea.com/gitnex/GitNex/pulls/525
Reviewed-by: M M Arif <mmarif@swatian.com>
2020-06-01 16:43:58 +00:00
4f0091f151 Improve layouts (#524)
make release checkboxes unchecked

admin users layout update

update commits and releases layout

profile fragments layout updates

improve labels

Merge branch 'master' into improve-layouts

branches and milestones layout update. Fix milestone infinite pagination loop for lower versions

layout updates for issues, pr. Fix pr nullable objects for lower versions

improve files layout

improve org info and list orgs

improve teams list layout by org

Fix repo layouts

Reviewed-on: https://gitea.com/gitnex/GitNex/pulls/524
Reviewed-by: opyale <opyale@noreply.gitea.io>
2020-06-01 15:53:56 +00:00
37367e142f Fixes for rc1 (#523)
Fix commits query limit

Fix text colors for auto theme

Fix text color in grid views

fix file size for dir

Reviewed-on: https://gitea.com/gitnex/GitNex/pulls/523
Reviewed-by: opyale <opyale@noreply.gitea.io>
2020-06-01 14:19:34 +00:00
556 changed files with 21268 additions and 9262 deletions

View File

@ -26,6 +26,12 @@ steps:
# depends_on: [ clone ]
# commands:
# - /opt/intellij/bin/idea.sh inspect/format ...
#
# - name: do-or-check-formatting
# image: dlsniper/docker-intellij
# depends_on: [ clone ]
# commands:
# - /opt/intellij/bin/idea.sh format -s .idea/codeStyles/Project.xml -m *.java app/src/main/java
trigger:
event:
@ -60,19 +66,19 @@ steps:
- name: build
image: nextcloudci/android:android-49
commands:
- ./gradlew build
- ./gradlew assembleFreeRelease
- name: sign
image: nextcloudci/android:android-49
environment:
TOKEN:
BOT_TOKEN:
from_secret: BOT_TOKEN
KS_PASS:
from_secret: KS_PASS
KEY_PASS:
from_secret: KEY_PASS
OUTPUT: signed.apk
GITEA: https://gitea.com
INSTANCE: https://codeberg.org
KS_FILE: ci_keystore.jks
KS_REPO:
from_secret: KS_REPO
@ -88,7 +94,7 @@ steps:
PLUGIN_FILE: 'signed.apk'
PLUGIN_TIMEOUT: 180
PLUGIN_ATTEMPTS: 5
PLUGIN_DESTINATION: 'https://cloud.swatian.com/remote.php/dav/files/GitNexBot/GitNex-Builds/latest.apk'
PLUGIN_DESTINATION: 'https://cloud.swatian.com/remote.php/dav/files/GitNexBot/gitnex/builds/latest.apk'
PLUGIN_CUSTOM_ARGUMENTS: '--progress-bar'
trigger:

View File

@ -4,14 +4,22 @@ end_of_line = lf
indent_size = 4
indent_style = space
insert_final_newline = true
trim_trailing_whitespace = true
max_line_length = 150
[*.java]
indent_style = tab
max_line_length = 220
line_comment = //
block_comment_start = /*
block_comment = *
block_comment_end = */
[*.json]
indent_size = 2
[{*.yml,*.yaml}]
indent_size = 2
[*.md]
trim_trailing_whitespace = false
insert_final_newline = false

3
.gitignore vendored
View File

@ -11,6 +11,9 @@
# Release dir
app/release/*
# Pro dir
app/pro/*
# Files for the ART/Dalvik VM
*.dex

68
.gitlab-ci.yml Normal file
View File

@ -0,0 +1,68 @@
stages:
- test
- build
- sign
- publish
test:
image: nextcloudci/android:android-49
stage: test
only:
- master
- tags
script:
- ./gradlew test
build:
image: nextcloudci/android:android-49
stage: build
only:
- master
- tags
script:
- ./gradlew assembleFreeRelease
artifacts:
paths:
- app/build/outputs/
expire_in: 15 minutes
sign:
image: nextcloudci/android:android-49
stage: sign
only:
- master
- tags
variables:
OUTPUT: "signed.apk"
INSTANCE: "https://codeberg.org"
KS_FILE: "ci_keystore.jks"
script:
- ./scripts/sign-build.sh
artifacts:
paths:
- signed.apk
expire_in: 15 minutes
latest:
image: tutum/curl
stage: publish
only:
- master
variables:
WEBDAV_USERNAME: "GitNexBot"
PLUGIN_FILE: "signed.apk"
PLUGIN_DESTINATION: "https://cloud.swatian.com/remote.php/dav/files/GitNexBot/gitnex/builds/latest.apk"
script:
- curl -T "$PLUGIN_FILE" -u "$WEBDAV_USERNAME":"$WEBDAV_PASSWORD" "$PLUGIN_DESTINATION"
release:
image: tutum/curl
stage: publish
only:
- tags
variables:
WEBDAV_USERNAME: "GitNexBot"
PLUGIN_FILE: "signed.apk"
script:
- "[[ $CI_COMMIT_REF_NAME == *'-rc'* ]] && echo 'Upload blocked. Build seems to be a release candidate.' && exit 0"
- curl -T "$PLUGIN_FILE" -u "$WEBDAV_USERNAME":"$WEBDAV_PASSWORD" 'https://cloud.swatian.com/remote.php/dav/files/GitNexBot/gitnex/releases/'"$CI_COMMIT_REF_NAME"'.apk'

View File

@ -16,6 +16,24 @@
</value>
</option>
</JavaCodeStyleSettings>
<JetCodeStyleSettings>
<option name="PACKAGES_TO_USE_STAR_IMPORTS">
<value>
<package name="java.util" alias="false" withSubpackages="false" />
<package name="kotlinx.android.synthetic" alias="false" withSubpackages="true" />
<package name="io.ktor" alias="false" withSubpackages="true" />
</value>
</option>
<option name="PACKAGES_IMPORT_LAYOUT">
<value>
<package name="" alias="false" withSubpackages="true" />
<package name="java" alias="false" withSubpackages="true" />
<package name="javax" alias="false" withSubpackages="true" />
<package name="kotlin" alias="false" withSubpackages="true" />
<package name="" alias="true" withSubpackages="true" />
</value>
</option>
</JetCodeStyleSettings>
<codeStyleSettings language="JAVA">
<option name="RIGHT_MARGIN" value="220" />
<option name="KEEP_LINE_BREAKS" value="false" />
@ -29,6 +47,7 @@
<option name="ELSE_ON_NEW_LINE" value="true" />
<option name="CATCH_ON_NEW_LINE" value="true" />
<option name="FINALLY_ON_NEW_LINE" value="true" />
<option name="ALIGN_MULTILINE_PARAMETERS" value="false" />
<option name="SPACE_BEFORE_IF_PARENTHESES" value="false" />
<option name="SPACE_BEFORE_WHILE_PARENTHESES" value="false" />
<option name="SPACE_BEFORE_FOR_PARENTHESES" value="false" />
@ -36,8 +55,13 @@
<option name="SPACE_BEFORE_CATCH_PARENTHESES" value="false" />
<option name="SPACE_BEFORE_SWITCH_PARENTHESES" value="false" />
<option name="SPACE_BEFORE_SYNCHRONIZED_PARENTHESES" value="false" />
<option name="CALL_PARAMETERS_WRAP" value="1" />
<option name="METHOD_PARAMETERS_WRAP" value="1" />
<option name="THROWS_LIST_WRAP" value="1" />
<option name="METHOD_CALL_CHAIN_WRAP" value="1" />
<option name="TERNARY_OPERATION_WRAP" value="1" />
<option name="ARRAY_INITIALIZER_WRAP" value="1" />
<option name="IF_BRACE_FORCE" value="3" />
<option name="WRAP_ON_TYPING" value="1" />
<indentOptions>
<option name="USE_TAB_CHARACTER" value="true" />
<option name="SMART_TABS" value="true" />

View File

@ -1,2 +1,2 @@
# Changelog
[Check out the release notes](https://gitea.com/gitnex/GitNex/releases)
[Check out the release notes](https://codeberg.org/gitnex/GitNex/releases)

View File

@ -10,7 +10,7 @@ Please ask if you are not sure about the scope of work to be submitted to avoid
**Code Standards**
Please follow the code standards, this will help other developers to understand your code too.
It also helps maintaining the code afterwards.
It is documented in the Wiki: [Code-Standards](https://gitea.com/gitnex/GitNex/wiki/Code-Standards)
It is documented in the Wiki: [Code-Standards](https://codeberg.org/gitnex/GitNex/wiki/Code-Standards)
**How to submit a PR**
Fork this repository. Pull the forked repository from your namespace to your local machine. Create new branch and work on the bug/feature/enhancement you would like to submit. Push it to your forked version. From there create Pull Request(PR) against **master** branch.

View File

@ -3,6 +3,7 @@ This part lists all PUBLIC individuals having contributed content to the code.
* M M Arif (mmarif)
* 6543
* opyale
* Unpublished
# Translators

45
LICENSE
View File

@ -1,7 +1,7 @@
GNU GENERAL PUBLIC LICENSE
Version 3, 29 June 2007
Copyright (C) 2007 Free Software Foundation, Inc. <http://fsf.org/>
Copyright (C) 2007 Free Software Foundation, Inc. <https://fsf.org/>
Everyone is permitted to copy and distribute verbatim copies
of this license document, but changing it is not allowed.
@ -620,19 +620,8 @@ copy of the Program in return for a fee.
END OF TERMS AND CONDITIONS
How to Apply These Terms to Your New Programs
If you develop a new program, and you want it to be of the greatest
possible use to the public, the best way to achieve this is to make it
free software which everyone can redistribute and change under these terms.
To do so, attach the following notices to the program. It is safest
to attach them to the start of each source file to most effectively
state the exclusion of warranty; and each file should have at least
the "copyright" line and a pointer to where the full notice is found.
Mastalab is a Mastodon client for Android devices
Copyright (C) 2017 Thomas Schneider
GitNex is an Android client/application for Gitea.
Copyright (C) 2019 The GitNex Authors
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
@ -645,30 +634,4 @@ the "copyright" line and a pointer to where the full notice is found.
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
Also add information on how to contact you by electronic and paper mail.
If the program does terminal interaction, make it output a short
notice like this when it starts in an interactive mode:
Mastalab Copyright (C) 2017 Thomas Schneider
This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
This is free software, and you are welcome to redistribute it
under certain conditions; type `show c' for details.
The hypothetical commands `show w' and `show c' should show the appropriate
parts of the General Public License. Of course, your program's commands
might be different; for a GUI interface, you would use an "about box".
You should also get your employer (if you work as a programmer) or school,
if any, to sign a "copyright disclaimer" for the program, if necessary.
For more information on this, and how to apply and follow the GNU GPL, see
<http://www.gnu.org/licenses/>.
The GNU General Public License does not permit incorporating your program
into proprietary programs. If your program is a subroutine library, you
may consider it more useful to permit linking proprietary applications with
the library. If this is what you want to do, use the GNU Lesser General
Public License instead of this License. But first, please read
<http://www.gnu.org/philosophy/why-not-lgpl.html>.
along with this program. If not, see <https://www.gnu.org/licenses/>.

View File

@ -1,4 +1,4 @@
[![License: GPL v3](https://img.shields.io/badge/License-GPL%20v3-blue.svg)](https://www.gnu.org/licenses/gpl-3.0) [![Release](https://img.shields.io/badge/dynamic/json.svg?label=release&url=https://gitea.com/api/v1/repos/gitnex/GitNex/releases&query=$[0].tag_name)](https://gitea.com/gitnex/GitNex/releases) [![Build Status](https://drone.gitea.com/api/badges/gitnex/GitNex/status.svg)](https://drone.gitea.com/gitnex/GitNex) [![Crowdin](https://badges.crowdin.net/gitnex/localized.svg)](https://crowdin.com/project/gitnex) [![Join the Discord chat at https://discord.gg/FbSS4rf](https://img.shields.io/discord/632219664587685908.svg)](https://discord.gg/FbSS4rf)
[![License: GPL v3](https://img.shields.io/badge/License-GPL%20v3-blue.svg)](https://www.gnu.org/licenses/gpl-3.0) ![Pipeline status](https://img.shields.io/gitlab/pipeline/opyale/gitnex/master) [![Release](https://img.shields.io/badge/dynamic/json.svg?label=release&url=https://codeberg.org/api/v1/repos/gitnex/GitNex/releases&query=$[0].tag_name)](https://codeberg.org/gitnex/GitNex/releases) [![Crowdin](https://badges.crowdin.net/gitnex/localized.svg)](https://crowdin.com/project/gitnex) [![Join the Discord chat at https://discord.gg/FbSS4rf](https://img.shields.io/discord/632219664587685908.svg)](https://discord.gg/FbSS4rf)
[<img alt="Become a Patroen" src="https://c5.patreon.com/external/logo/become_a_patron_button@2x.png" height="40"/>](https://www.patreon.com/mmarif) [<img alt="Donate using Liberapay" src="https://liberapay.com/assets/widgets/donate.svg" height="40"/>](https://liberapay.com/mmarif/donate)
@ -11,62 +11,64 @@ GitNex is licensed under GPLv3 License. See the LICENSE file for the full licens
## Downloads
[<img alt='Get it on F-droid' src='https://gitlab.com/fdroid/artwork/raw/master/badge/get-it-on.png' height="80"/>](https://f-droid.org/en/packages/org.mian.gitnex/)
[<img alt='Get it on Google Play' src='https://play.google.com/intl/en_us/badges/images/generic/en_badge_web_generic.png' height="80"/>](https://play.google.com/store/apps/details?id=org.mian.gitnex)
[<img alt='Download APK' src='https://gitnex.com/img/download-apk.png' height="80"/>](https://cloud.swatian.com/s/QoDFzMxmnf2FfYw)
Download latest build from master: [https://cloud.swatian.com/s/Cq592xGEfnsGAAW](https://cloud.swatian.com/s/Cq592xGEfnsGAAW)
[<img alt='Download builds and releases' src='assets/apk-badge.png' height="82"/>](https://cloud.swatian.com/s/DN7E5xxtaw4fRbE)
## Note about Gitea version
Please make sure that you are on latest stable release or later for better app experience.
Check the versions [compatibility page](https://gitea.com/gitnex/GitNex/wiki/Compatibility) which lists all the supported versions with compatibility ratio.
Check the versions [compatibility page](https://codeberg.org/gitnex/GitNex/wiki/Compatibility) which lists all the supported versions with compatibility ratio.
## Build from source
Option 1 - Download the source code, open it in Android Studio and build it there.
Option 2 - Open terminal(Linux) and cd to the project dir. Run `./gradlew build`.
Option 2 - Open terminal(Linux) and cd to the project dir. Run `./gradlew assembleFree`.
## Features
- Multiple accounts support
- File and directory browser
- File viewer
- Create files
- Explore repositories
- Issues list
- Pull requests
- Merge pull request
- [MANY MORE](https://gitea.com/gitnex/GitNex/wiki/Features)
- Files diff for PRs
- Notifications
- Drafts
- Repositories / issues / org list
- [MANY MORE](https://codeberg.org/gitnex/GitNex/wiki/Features)
## Contributing
[CONTRIBUTING](https://gitea.com/gitnex/GitNex/src/branch/master/CONTRIBUTING.md)
[CONTRIBUTING](https://codeberg.org/gitnex/GitNex/src/branch/master/CONTRIBUTING.md)
## Translation
Help us translate GitNex to your native language.
We use [Crowdin](https://crowdin.com/project/gitnex) for translation. If your language is not listed, please request [here](https://gitea.com/gitnex/GitNex/issues) to add it to the project.
We use [Crowdin](https://crowdin.com/project/gitnex) for translation. If your language is not listed, please request [here](https://codeberg.org/gitnex/GitNex/issues) to add it to the project.
**Link: https://crowdin.com/project/GitNex**
## Screenshots:
<img src="https://gitea.com/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/001.png" alt="001.png" width="200"/> | <img src="https://gitea.com/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/002.png" alt="002.png" width="200"/> | <img src="https://gitea.com/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/003.png" alt="003.png" width="200"/> | <img src="https://gitea.com/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/004.png" alt="004.png" width="200"/>
<img src="https://codeberg.org/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/001.png" alt="001.png" width="200"/> | <img src="https://codeberg.org/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/002.png" alt="002.png" width="200"/> | <img src="https://codeberg.org/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/003.png" alt="003.png" width="200"/> | <img src="https://codeberg.org/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/004.png" alt="004.png" width="200"/>
---|---|---|---
<img src="https://gitea.com/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/005.png" alt="005.png" width="200"/> | <img src="https://gitea.com/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/006.png" alt="006.png" width="200"/> | <img src="https://gitea.com/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/007.png" alt="007.png" width="200"/> | <img src="https://gitea.com/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/008.png" alt="008.png" width="200"/>
<img src="https://codeberg.org/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/005.png" alt="005.png" width="200"/> | <img src="https://codeberg.org/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/006.png" alt="006.png" width="200"/> | <img src="https://codeberg.org/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/007.png" alt="007.png" width="200"/> | <img src="https://codeberg.org/gitnex/GitNex/raw/branch/master/fastlane/metadata/android/en-US/images/phoneScreenshots/008.png" alt="008.png" width="200"/>
## FAQ
[Faq](https://gitea.com/gitnex/GitNex/wiki/FAQ)
[Faq](https://codeberg.org/gitnex/GitNex/wiki/FAQ)
## Links
[Website](https://gitnex.com)
[Wiki](https://gitea.com/gitnex/GitNex/wiki/Home)
[Wiki](https://codeberg.org/gitnex/GitNex/wiki/Home)
[Website Repository](https://gitlab.com/mmarif4u/gitnex-website)
[Troubleshoot Guide](https://gitea.com/gitnex/GitNex/wiki/Troubleshoot-Guide)
[Troubleshoot Guide](https://codeberg.org/gitnex/GitNex/wiki/Troubleshoot-Guide)
## Thanks
Thanks to all the open source libraries, contributors and donators.
Open source libraries
#### Open source libraries
- Retrofit
- Gson
- Okhttp
@ -85,7 +87,9 @@ Open source libraries
- Apache/commons-io
- Caverock/androidsvg
- Droidsonroids.gif/android-gif-drawable
- Barteksc/AndroidPdfViewer
- Ge0rg/MemorizingTrustManager
- Barteksc/androidPdfViewer
- Ge0rg/memorizingTrustManager
- Dimezis/blurView
- Mikaelhg/urlbuilder
[Follow me on Fediverse - mastodon.social/@mmarif](https://mastodon.social/@mmarif)

View File

@ -1,17 +1,30 @@
apply plugin: 'com.android.application'
android {
compileSdkVersion 29
compileSdkVersion 30
defaultConfig {
applicationId "org.mian.gitnex"
minSdkVersion 21
targetSdkVersion 29
versionCode 295
versionName "3.0.0-rc1"
targetSdkVersion 30
versionCode 317
versionName "3.2.0-rc1"
multiDexEnabled true
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
viewBinding {
enabled = true
dexOptions {
javaMaxHeapSize "4g"
}
flavorDimensions "default"
productFlavors {
free {
applicationId "org.mian.gitnex"
}
pro {
applicationId "org.mian.gitnex.pro"
}
}
buildFeatures {
viewBinding = true
}
buildTypes {
release {
@ -28,6 +41,9 @@ android {
targetCompatibility = "8"
sourceCompatibility = "8"
}
defaultConfig{
vectorDrawables.useSupportLibrary = true
}
}
configurations {
@ -36,27 +52,29 @@ configurations {
}
dependencies {
def lifecycle_version = "2.2.0"
def markwon_version = '4.3.1'
def lifecycle_version = '2.3.0-alpha07'
def markwon_version = '4.6.0'
def work_version = "2.4.0"
def acra = "5.5.0"
implementation fileTree(include: ['*.jar'], dir: 'libs')
implementation "androidx.appcompat:appcompat:1.2.0-rc01"
implementation "com.google.android.material:material:1.2.0-beta01"
implementation "androidx.constraintlayout:constraintlayout:1.1.3"
implementation 'androidx.appcompat:appcompat:1.3.0-alpha02'
implementation "com.google.android.material:material:1.3.0-alpha02"
implementation 'androidx.constraintlayout:constraintlayout:2.0.1'
implementation "androidx.legacy:legacy-support-v4:1.0.0"
implementation "androidx.lifecycle:lifecycle-viewmodel:$lifecycle_version"
testImplementation "junit:junit:4.13"
androidTestImplementation "androidx.test:runner:1.2.0"
androidTestImplementation "androidx.test.espresso:espresso-core:3.2.0"
androidTestImplementation 'androidx.test:runner:1.3.0'
androidTestImplementation 'androidx.test.espresso:espresso-core:3.3.0'
implementation "com.github.vihtarb:tooltip:0.2.0"
implementation 'com.squareup.okhttp3:okhttp:4.7.0'
implementation 'com.squareup.okhttp3:okhttp:4.9.0'
implementation "com.google.code.gson:gson:2.8.6"
implementation "com.squareup.picasso:picasso:2.71828"
implementation "com.amulyakhare:com.amulyakhare.textdrawable:1.0.1"
implementation 'com.squareup.retrofit2:retrofit:2.8.1'
implementation 'com.squareup.retrofit2:converter-gson:2.8.1'
implementation 'com.squareup.retrofit2:converter-scalars:2.8.1'
implementation 'com.squareup.okhttp3:logging-interceptor:4.7.0'
implementation 'com.squareup.retrofit2:retrofit:2.9.0'
implementation 'com.squareup.retrofit2:converter-gson:2.9.0'
implementation 'com.squareup.retrofit2:converter-scalars:2.9.0'
implementation 'com.squareup.okhttp3:logging-interceptor:4.9.0'
implementation 'org.ocpsoft.prettytime:prettytime:4.0.5.Final'
implementation "com.vdurmont:emoji-java:5.1.1"
implementation "com.pes.materialcolorpicker:library:1.2.5"
@ -77,14 +95,18 @@ dependencies {
implementation "pl.droidsonroids.gif:android-gif-drawable:1.2.19"
implementation "com.hendraanggrian.appcompat:socialview:0.2"
implementation "com.hendraanggrian.appcompat:socialview-commons:0.2"
implementation "androidx.lifecycle:lifecycle-extensions:$lifecycle_version"
implementation "androidx.lifecycle:lifecycle-viewmodel:$lifecycle_version"
implementation "com.github.HamidrezaAmz:BreadcrumbsView:0.2.9"
implementation "commons-io:commons-io:20030203.000550"
implementation 'org.apache.commons:commons-lang3:3.11'
implementation "com.github.chrisbanes:PhotoView:2.3.0"
implementation "com.github.barteksc:android-pdf-viewer:3.2.0-beta.1"
implementation "ch.acra:acra-mail:$acra"
implementation "ch.acra:acra-limiter:$acra"
implementation "ch.acra:acra-notification:$acra"
implementation "androidx.room:room-runtime:2.2.5"
annotationProcessor "androidx.room:room-compiler:2.2.5"
implementation "androidx.work:work-runtime:$work_version"
implementation "com.eightbitlab:blurview:1.6.3"
implementation "io.mikael:urlbuilder:2.0.9"
}

View File

@ -4,6 +4,7 @@
package="org.mian.gitnex">
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.VIBRATE" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<application
@ -11,9 +12,11 @@
android:icon="@mipmap/app_logo"
android:label="@string/app_name"
android:networkSecurityConfig="@xml/network_security_config"
android:resizeableActivity="true"
android:roundIcon="@mipmap/app_logo_round"
android:supportsRtl="true"
tools:targetApi="n">
<activity android:name=".activities.MergePullRequestActivity" />
<activity
android:name=".activities.FileViewActivity"
@ -45,8 +48,6 @@
android:name=".activities.OrganizationDetailActivity"
android:label="@string/title_activity_org_detail"
android:theme="@style/AppTheme.NoActionBar" />
<activity android:name=".activities.SponsorsActivity" />
<activity android:name=".activities.CreditsActivity" />
<activity android:name=".activities.CreateLabelActivity" />
<activity android:name=".activities.CreateIssueActivity" />
<activity android:name=".activities.CreateMilestoneActivity" />
@ -58,7 +59,7 @@
android:name=".activities.RepoDetailActivity"
android:label="@string/title_activity_repo_detail"
android:theme="@style/AppTheme.NoActionBar" />
<activity android:name=".activities.MainActivity" android:theme="@android:style/Theme.NoTitleBar">
<activity android:name=".activities.MainActivity" android:theme="@android:style/Theme.NoTitleBar" android:configChanges="orientation|screenSize|smallestScreenSize|density|screenLayout|uiMode|keyboard|keyboardHidden|navigation">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
@ -80,6 +81,17 @@
<activity android:name=".activities.SettingsTranslationActivity" />
<activity android:name=".activities.SettingsReportsActivity" />
<activity android:name=".activities.AddNewTeamMemberActivity" />
<activity android:name=".activities.SettingsDraftsActivity" />
<activity android:name=".activities.RepoForksActivity" />
<activity android:name=".activities.AddNewAccountActivity" />
<activity android:name=".activities.RepositorySettingsActivity" />
<activity android:name=".activities.CreatePullRequestActivity" />
<!-- Version < 3.0. DeX Mode and Screen Mirroring support -->
<meta-data android:name="com.samsung.android.keepalive.density" android:value="true"/>
<!-- Version >= 3.0. DeX Dual Mode support -->
<meta-data android:name="com.samsung.android.multidisplay.keep_process_alive" android:value="true"/>
</application>
</manifest>

Binary file not shown.

After

Width:  |  Height:  |  Size: 16 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 15 KiB

View File

@ -2,16 +2,16 @@ package org.mian.gitnex.actions;
import android.content.Context;
import android.util.Log;
import androidx.annotation.NonNull;
import org.mian.gitnex.R;
import org.mian.gitnex.activities.AddCollaboratorToRepositoryActivity;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.Collaborators;
import org.mian.gitnex.models.Permission;
import org.mian.gitnex.util.TinyDB;
import androidx.annotation.NonNull;
import retrofit2.Call;
import retrofit2.Callback;
@ -47,7 +47,7 @@ public class CollaboratorActions {
if(response.isSuccessful()) {
if(response.code() == 204) {
Toasty.info(context, context.getString(R.string.removeCollaboratorToastText));
Toasty.success(context, context.getString(R.string.removeCollaboratorToastText));
((AddCollaboratorToRepositoryActivity)context).finish();
//Log.i("addCollaboratorSearch", addCollaboratorSearch.getText().toString());
//tinyDb.putBoolean("updateDataSet", true);
@ -66,17 +66,17 @@ public class CollaboratorActions {
}
else if(response.code() == 403) {
Toasty.info(context, context.getString(R.string.authorizeError));
Toasty.error(context, context.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(context, context.getString(R.string.apiNotFound));
Toasty.warning(context, context.getString(R.string.apiNotFound));
}
else {
Toasty.info(context, context.getString(R.string.genericError));
Toasty.error(context, context.getString(R.string.genericError));
}
@ -117,7 +117,7 @@ public class CollaboratorActions {
if(response.isSuccessful()) {
if(response.code() == 204) {
Toasty.info(context, context.getString(R.string.addCollaboratorToastText));
Toasty.success(context, context.getString(R.string.addCollaboratorToastText));
((AddCollaboratorToRepositoryActivity)context).finish();
//AddCollaboratorToRepositoryActivity usersSearchData = new AddCollaboratorToRepositoryActivity();
//usersSearchData.loadUserSearchList(instanceUrl, instanceToken, searchKeyword, context);
@ -134,17 +134,17 @@ public class CollaboratorActions {
}
else if(response.code() == 403) {
Toasty.info(context, context.getString(R.string.authorizeError));
Toasty.error(context, context.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(context, context.getString(R.string.apiNotFound));
Toasty.warning(context, context.getString(R.string.apiNotFound));
}
else {
Toasty.info(context, context.getString(R.string.genericError));
Toasty.error(context, context.getString(R.string.genericError));
}

View File

@ -7,12 +7,13 @@ import com.google.gson.JsonElement;
import org.mian.gitnex.R;
import org.mian.gitnex.activities.ReplyToIssueActivity;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.DraftsApi;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.IssueComments;
import org.mian.gitnex.models.UpdateIssueState;
import org.mian.gitnex.util.TinyDB;
import retrofit2.Call;
import retrofit2.Callback;
@ -22,7 +23,7 @@ import retrofit2.Callback;
public class IssueActions {
public static void editIssueComment(final Context ctx, final int commentId, final String commentBody) {
public static void editIssueComment(final Context ctx, final int commentId, final String commentBody, long draftIdOnCreate) {
final TinyDB tinyDb = new TinyDB(ctx);
final String instanceUrl = tinyDb.getString("instanceUrl");
@ -48,6 +49,10 @@ public class IssueActions {
tinyDb.putBoolean("commentEdited", true);
Toasty.info(ctx, ctx.getString(R.string.editCommentUpdatedText));
DraftsApi draftsApi = new DraftsApi(ctx);
draftsApi.deleteSingleDraft((int) draftIdOnCreate);
((ReplyToIssueActivity) ctx).finish();
}
@ -59,17 +64,17 @@ public class IssueActions {
}
else if(response.code() == 403) {
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else {
Toasty.info(ctx, ctx.getString(R.string.genericError));
Toasty.error(ctx, ctx.getString(R.string.genericError));
}
@ -113,13 +118,13 @@ public class IssueActions {
if(issueState.equals("closed")) {
Toasty.info(ctx, ctx.getString(R.string.issueStateClosed));
Toasty.success(ctx, ctx.getString(R.string.issueStateClosed));
tinyDb.putString("issueState", "closed");
}
else if(issueState.equals("open")) {
Toasty.info(ctx, ctx.getString(R.string.issueStateReopened));
Toasty.success(ctx, ctx.getString(R.string.issueStateReopened));
tinyDb.putString("issueState", "open");
}
@ -133,17 +138,17 @@ public class IssueActions {
}
else if(response.code() == 403) {
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else {
Toasty.info(ctx, ctx.getString(R.string.genericError));
Toasty.error(ctx, ctx.getString(R.string.genericError));
}
@ -184,14 +189,14 @@ public class IssueActions {
if(response.code() == 201) {
Toasty.info(ctx, ctx.getString(R.string.subscribedSuccessfully));
Toasty.success(ctx, ctx.getString(R.string.subscribedSuccessfully));
tinyDB.putBoolean("issueSubscribed", true);
}
else if(response.code() == 200) {
tinyDB.putBoolean("issueSubscribed", true);
Toasty.info(ctx, ctx.getString(R.string.alreadySubscribed));
Toasty.success(ctx, ctx.getString(R.string.alreadySubscribed));
}
@ -203,7 +208,7 @@ public class IssueActions {
}
else {
Toasty.info(ctx, ctx.getString(R.string.subscribtionError));
Toasty.error(ctx, ctx.getString(R.string.subscriptionError));
}
@ -212,7 +217,7 @@ public class IssueActions {
@Override
public void onFailure(@NonNull Call<Void> call, @NonNull Throwable t) {
Toasty.info(ctx, ctx.getString(R.string.unsubscribedSuccessfully));
Toasty.success(ctx, ctx.getString(R.string.unsubscribedSuccessfully));
}
});
@ -244,14 +249,14 @@ public class IssueActions {
if(response.code() == 201) {
Toasty.info(ctx, ctx.getString(R.string.unsubscribedSuccessfully));
Toasty.success(ctx, ctx.getString(R.string.unsubscribedSuccessfully));
tinyDB.putBoolean("issueSubscribed", false);
}
else if(response.code() == 200) {
tinyDB.putBoolean("issueSubscribed", false);
Toasty.info(ctx, ctx.getString(R.string.alreadyUnsubscribed));
Toasty.success(ctx, ctx.getString(R.string.alreadyUnsubscribed));
}
@ -263,7 +268,7 @@ public class IssueActions {
}
else {
Toasty.info(ctx, ctx.getString(R.string.unsubscribtionError));
Toasty.error(ctx, ctx.getString(R.string.unsubscriptionError));
}
@ -272,7 +277,7 @@ public class IssueActions {
@Override
public void onFailure(@NonNull Call<Void> call, @NonNull Throwable t) {
Toasty.info(ctx, ctx.getString(R.string.unsubscribtionError));
Toasty.error(ctx, ctx.getString(R.string.unsubscriptionError));
}
});
}

View File

@ -7,9 +7,9 @@ import com.google.gson.JsonElement;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.Milestones;
import org.mian.gitnex.util.TinyDB;
import retrofit2.Call;
import retrofit2.Callback;
@ -48,7 +48,7 @@ public class MilestoneActions {
if(response.isSuccessful()) {
Toasty.info(ctx, ctx.getString(R.string.milestoneStatusUpdate));
Toasty.success(ctx, ctx.getString(R.string.milestoneStatusUpdate));
}
else if(response.code() == 401) {
@ -61,7 +61,7 @@ public class MilestoneActions {
}
else {
Toasty.info(ctx, ctx.getString(R.string.genericError));
Toasty.error(ctx, ctx.getString(R.string.genericError));
}
@ -106,7 +106,7 @@ public class MilestoneActions {
if(response.isSuccessful()) {
Toasty.info(ctx, ctx.getString(R.string.milestoneStatusUpdate));
Toasty.success(ctx, ctx.getString(R.string.milestoneStatusUpdate));
}
else if(response.code() == 401) {
@ -119,7 +119,7 @@ public class MilestoneActions {
}
else {
Toasty.info(ctx, ctx.getString(R.string.genericError));
Toasty.error(ctx, ctx.getString(R.string.genericError));
}

View File

@ -0,0 +1,59 @@
package org.mian.gitnex.actions;
import android.content.Context;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.NotificationThread;
import java.io.IOException;
import java.util.Date;
import okhttp3.ResponseBody;
import retrofit2.Call;
/**
* Author opyale
*/
public class NotificationsActions {
public enum NotificationStatus {READ, UNREAD, PINNED}
private TinyDB tinyDB;
private Context context;
private String instanceUrl;
private String instanceToken;
public NotificationsActions(Context context) {
this.context = context;
this.tinyDB = new TinyDB(context);
String loginUid = tinyDB.getString("loginUid");
instanceUrl = tinyDB.getString("instanceUrl");
instanceToken = "token " + tinyDB.getString(loginUid + "-token");
}
public void setNotificationStatus(NotificationThread notificationThread, NotificationStatus notificationStatus) throws IOException {
Call<ResponseBody> call = RetrofitClient.getInstance(instanceUrl, context).getApiInterface()
.markNotificationThreadAsRead(instanceToken, notificationThread.getId(), notificationStatus.name());
if(!call.execute().isSuccessful()) {
throw new IllegalStateException();
}
}
public boolean setAllNotificationsRead(Date date) throws IOException {
Call<ResponseBody> call = RetrofitClient.getInstance(instanceUrl, context).getApiInterface()
.markNotificationThreadsAsRead(instanceToken, AppUtil.getTimestampFromDate(context, date), true,
new String[]{"unread", "pinned"}, "read");
return call.execute().isSuccessful();
}
}

View File

@ -8,8 +8,8 @@ import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.util.TinyDB;
import retrofit2.Call;
import retrofit2.Callback;
@ -46,7 +46,7 @@ public class RepositoryActions {
if(response.code() == 204) {
tinyDb.putBoolean("repoCreated", true);
Toasty.info(context, context.getString(R.string.starRepositorySuccess));
Toasty.success(context, context.getString(R.string.starRepositorySuccess));
}
}
@ -60,17 +60,17 @@ public class RepositoryActions {
}
else if(response.code() == 403) {
Toasty.info(context, context.getString(R.string.authorizeError));
Toasty.error(context, context.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(context, context.getString(R.string.apiNotFound));
Toasty.warning(context, context.getString(R.string.apiNotFound));
}
else {
Toasty.info(context, context.getString(R.string.genericError));
Toasty.error(context, context.getString(R.string.genericError));
}
@ -111,7 +111,7 @@ public class RepositoryActions {
if(response.code() == 204) {
tinyDb.putBoolean("repoCreated", true);
Toasty.info(context, context.getString(R.string.unStarRepositorySuccess));
Toasty.success(context, context.getString(R.string.unStarRepositorySuccess));
}
}
@ -125,17 +125,17 @@ public class RepositoryActions {
}
else if(response.code() == 403) {
Toasty.info(context, context.getString(R.string.authorizeError));
Toasty.error(context, context.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(context, context.getString(R.string.apiNotFound));
Toasty.warning(context, context.getString(R.string.apiNotFound));
}
else {
Toasty.info(context, context.getString(R.string.genericError));
Toasty.error(context, context.getString(R.string.genericError));
}
@ -176,7 +176,7 @@ public class RepositoryActions {
if(response.code() == 200) {
tinyDb.putBoolean("repoCreated", true);
Toasty.info(context, context.getString(R.string.watchRepositorySuccess));
Toasty.success(context, context.getString(R.string.watchRepositorySuccess));
}
}
@ -190,17 +190,17 @@ public class RepositoryActions {
}
else if(response.code() == 403) {
Toasty.info(context, context.getString(R.string.authorizeError));
Toasty.error(context, context.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(context, context.getString(R.string.apiNotFound));
Toasty.warning(context, context.getString(R.string.apiNotFound));
}
else {
Toasty.info(context, context.getString(R.string.genericError));
Toasty.error(context, context.getString(R.string.genericError));
}
@ -240,7 +240,7 @@ public class RepositoryActions {
if(response.code() == 204) {
tinyDb.putBoolean("repoCreated", true);
Toasty.info(context, context.getString(R.string.unWatchRepositorySuccess));
Toasty.success(context, context.getString(R.string.unWatchRepositorySuccess));
}
else if(response.code() == 401) {
@ -253,17 +253,17 @@ public class RepositoryActions {
}
else if(response.code() == 403) {
Toasty.info(context, context.getString(R.string.authorizeError));
Toasty.error(context, context.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(context, context.getString(R.string.apiNotFound));
Toasty.warning(context, context.getString(R.string.apiNotFound));
}
else {
Toasty.info(context, context.getString(R.string.genericError));
Toasty.error(context, context.getString(R.string.genericError));
}

View File

@ -8,8 +8,8 @@ import org.mian.gitnex.activities.AddNewTeamMemberActivity;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.util.TinyDB;
import retrofit2.Call;
import retrofit2.Callback;
@ -43,7 +43,7 @@ public class TeamActions {
if(response.code() == 204) {
tinyDb.putBoolean("teamActionFlag", true);
Toasty.info(context, context.getString(R.string.memberRemovedMessage));
Toasty.success(context, context.getString(R.string.memberRemovedMessage));
((AddNewTeamMemberActivity)context).finish();
}
@ -59,17 +59,17 @@ public class TeamActions {
}
else if(response.code() == 403) {
Toasty.info(context, context.getString(R.string.authorizeError));
Toasty.error(context, context.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(context, context.getString(R.string.apiNotFound));
Toasty.warning(context, context.getString(R.string.apiNotFound));
}
else {
Toasty.info(context, context.getString(R.string.genericError));
Toasty.error(context, context.getString(R.string.genericError));
}
@ -109,7 +109,7 @@ public class TeamActions {
if(response.code() == 204) {
tinyDb.putBoolean("teamActionFlag", true);
Toasty.info(context, context.getString(R.string.memberAddedMessage));
Toasty.success(context, context.getString(R.string.memberAddedMessage));
((AddNewTeamMemberActivity)context).finish();
}
@ -125,17 +125,17 @@ public class TeamActions {
}
else if(response.code() == 403) {
Toasty.info(context, context.getString(R.string.authorizeError));
Toasty.error(context, context.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(context, context.getString(R.string.apiNotFound));
Toasty.warning(context, context.getString(R.string.apiNotFound));
}
else {
Toasty.info(context, context.getString(R.string.genericError));
Toasty.error(context, context.getString(R.string.genericError));
}

View File

@ -1,30 +1,29 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import android.content.Context;
import android.os.Bundle;
import android.util.Log;
import android.view.KeyEvent;
import android.view.View;
import android.view.inputmethod.EditorInfo;
import android.view.inputmethod.InputMethodManager;
import android.widget.ImageView;
import android.widget.ProgressBar;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.UserSearchAdapter;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.models.UserSearch;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.models.UserSearch;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
/**
* Author M M Arif
@ -145,5 +144,4 @@ public class AddCollaboratorToRepositoryActivity extends BaseActivity {
onClickListener = view -> finish();
}
}

View File

@ -0,0 +1,268 @@
package org.mian.gitnex.activities;
import android.content.Context;
import android.graphics.Color;
import android.graphics.drawable.ColorDrawable;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.ArrayAdapter;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AlertDialog;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.UserAccountsApi;
import org.mian.gitnex.databinding.ActivityAddNewAccountBinding;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.PathsHelper;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.UrlHelper;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.GiteaVersion;
import org.mian.gitnex.models.UserInfo;
import java.net.URI;
import io.mikael.urlbuilder.UrlBuilder;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
*/
public class AddNewAccountActivity extends BaseActivity {
final Context ctx = this;
private Context appCtx;
private TinyDB tinyDB;
private View.OnClickListener onClickListener;
private ActivityAddNewAccountBinding viewBinding;
private enum Protocol {HTTPS, HTTP}
private String spinnerSelectedValue;
@Override
protected int getLayoutResourceId() {
return R.layout.activity_add_new_account;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
tinyDB = new TinyDB(appCtx);
viewBinding = ActivityAddNewAccountBinding.inflate(getLayoutInflater());
View view = viewBinding.getRoot();
setContentView(view);
getWindow().getDecorView().setBackground(new ColorDrawable(Color.TRANSPARENT));
initCloseListener();
viewBinding.close.setOnClickListener(onClickListener);
ArrayAdapter<Protocol> adapterProtocols = new ArrayAdapter<>(ctx, R.layout.list_spinner_items, Protocol.values());
viewBinding.protocolSpinner.setAdapter(adapterProtocols);
viewBinding.protocolSpinner.setOnItemClickListener((parent, view1, position, id) -> spinnerSelectedValue = String.valueOf(parent.getItemAtPosition(position)));
viewBinding.addNewAccount.setOnClickListener(login -> {
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
if(!connToInternet) {
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
}
else {
processLogin();
}
});
}
private void processLogin() {
try {
String instanceUrlET = String.valueOf(viewBinding.instanceUrl.getText());
String loginToken = String.valueOf(viewBinding.loginToken.getText());
String protocol = spinnerSelectedValue;
if(protocol == null) {
Toasty.error(ctx, getResources().getString(R.string.protocolEmptyError));
return;
}
if(instanceUrlET.equals("")) {
Toasty.error(ctx, getResources().getString(R.string.emptyFieldURL));
return;
}
if(loginToken.equals("")) {
Toasty.error(ctx, getResources().getString(R.string.loginTokenError));
return;
}
URI rawInstanceUrl = UrlBuilder.fromString(UrlHelper.fixScheme(instanceUrlET, "http")).toUri();
URI instanceUrl = UrlBuilder.fromUri(rawInstanceUrl).withScheme(protocol.toLowerCase()).withPath(PathsHelper.join(rawInstanceUrl.getPath(), "/api/v1/"))
.toUri();
versionCheck(instanceUrl.toString(), loginToken);
}
catch(Exception e) {
Log.e("onFailure-login", e.toString());
Toasty.error(ctx, getResources().getString(R.string.malformedUrl));
}
}
private void versionCheck(final String instanceUrl, final String loginToken) {
Call<GiteaVersion> callVersion;
callVersion = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().getGiteaVersionWithToken("token " + loginToken);
callVersion.enqueue(new Callback<GiteaVersion>() {
@Override
public void onResponse(@NonNull final Call<GiteaVersion> callVersion, @NonNull retrofit2.Response<GiteaVersion> responseVersion) {
if(responseVersion.code() == 200) {
GiteaVersion version = responseVersion.body();
assert version != null;
if(!Version.valid(version.getVersion())) {
Toasty.error(ctx, getResources().getString(R.string.versionUnknown));
return;
}
tinyDB.putString("giteaVersion", version.getVersion());
Version giteaVersion = new Version(version.getVersion());
if(giteaVersion.less(getString(R.string.versionLow))) {
AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder(ctx).setTitle(getString(R.string.versionAlertDialogHeader))
.setMessage(getResources().getString(R.string.versionUnsupportedOld, version.getVersion())).setIcon(R.drawable.ic_warning)
.setCancelable(true);
alertDialogBuilder.setNegativeButton(getString(R.string.cancelButton), (dialog, which) -> {
dialog.dismiss();
});
alertDialogBuilder.setPositiveButton(getString(R.string.textContinue), (dialog, which) -> {
dialog.dismiss();
login(instanceUrl, loginToken);
});
alertDialogBuilder.create().show();
}
else if(giteaVersion.lessOrEqual(getString(R.string.versionHigh))) {
login(instanceUrl, loginToken);
}
else {
Toasty.warning(ctx, getResources().getString(R.string.versionUnsupportedNew));
login(instanceUrl, loginToken);
}
}
else if(responseVersion.code() == 403) {
login(instanceUrl, loginToken);
}
}
private void login(String instanceUrl, String loginToken) {
setupNewAccountWithToken(instanceUrl, loginToken);
}
@Override
public void onFailure(@NonNull Call<GiteaVersion> callVersion, @NonNull Throwable t) {
Log.e("onFailure-versionCheck", t.toString());
Toasty.error(ctx, getResources().getString(R.string.errorOnLogin));
}
});
}
private void setupNewAccountWithToken(String instanceUrl, final String loginToken) {
Call<UserInfo> call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().getUserInfo("token " + loginToken);
call.enqueue(new Callback<UserInfo>() {
@Override
public void onResponse(@NonNull Call<UserInfo> call, @NonNull retrofit2.Response<UserInfo> response) {
UserInfo userDetails = response.body();
switch(response.code()) {
case 200:
assert userDetails != null;
// insert new account to db if does not exist
String accountName = userDetails.getUsername() + "@" + instanceUrl;
UserAccountsApi userAccountsApi = new UserAccountsApi(ctx);
int checkAccount = userAccountsApi.getCount(accountName);
if(checkAccount == 0) {
userAccountsApi.insertNewAccount(accountName, instanceUrl, userDetails.getUsername(), loginToken, "");
Toasty.success(ctx, getResources().getString(R.string.accountAddedMessage));
finish();
}
else {
Toasty.warning(ctx, getResources().getString(R.string.accountAlreadyExistsError));
}
break;
case 401:
Toasty.error(ctx, getResources().getString(R.string.unauthorizedApiError));
break;
default:
Toasty.error(ctx, getResources().getString(R.string.genericApiStatusError) + response.code());
}
}
@Override
public void onFailure(@NonNull Call<UserInfo> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
Toasty.error(ctx, getResources().getString(R.string.genericError));
}
});
}
private void initCloseListener() {
onClickListener = view -> finish();
}
}

View File

@ -18,9 +18,9 @@ import org.mian.gitnex.R;
import org.mian.gitnex.adapters.UserSearchForTeamMemberAdapter;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.models.UserSearch;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
@ -28,6 +28,10 @@ import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
/**
* Author M M Arif
*/
public class AddNewTeamMemberActivity extends BaseActivity {
private View.OnClickListener onClickListener;
@ -64,7 +68,7 @@ public class AddNewTeamMemberActivity extends BaseActivity {
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
ImageView closeActivity = findViewById(R.id.close);
addNewTeamMember = findViewById(R.id.addNewTeamMeber);
addNewTeamMember = findViewById(R.id.addNewTeamMember);
mRecyclerView = findViewById(R.id.recyclerViewUserSearch);
mProgressBar = findViewById(R.id.progress_bar);
noData = findViewById(R.id.noData);
@ -96,7 +100,7 @@ public class AddNewTeamMemberActivity extends BaseActivity {
@Override
public void onTextChanged(CharSequence s, int start, int before, int count) {
if(!addNewTeamMember.getText().toString().equals("")) {
if(!addNewTeamMember.getText().toString().equals("") && addNewTeamMember.getText().toString().length() > 1) {
adapter = new UserSearchForTeamMemberAdapter(dataList, ctx, Integer.parseInt(teamId));
loadUserSearchList(instanceUrl, instanceToken, addNewTeamMember.getText().toString(), loginUid, teamId);
@ -121,6 +125,8 @@ public class AddNewTeamMemberActivity extends BaseActivity {
Call<UserSearch> call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().getUserBySearch(Authorization.returnAuthentication(ctx, loginUid, token), searchKeyword, 10);
mProgressBar.setVisibility(View.VISIBLE);
call.enqueue(new Callback<UserSearch>() {
@Override

View File

@ -1,23 +1,23 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import android.content.Context;
import android.graphics.Color;
import android.graphics.drawable.ColorDrawable;
import android.os.Bundle;
import android.util.Log;
import androidx.annotation.NonNull;
import com.google.gson.JsonElement;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.MultiSelectDialog;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.Collaborators;
import org.mian.gitnex.models.Issues;
import org.mian.gitnex.models.MultiSelectModel;
import org.mian.gitnex.models.UpdateIssueAssignees;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import retrofit2.Call;
@ -139,7 +139,7 @@ public class AddRemoveAssigneesActivity extends BaseActivity {
.multiSelectList(listOfCollaborators)
.onSubmit(new MultiSelectDialog.SubmitCallbackListener() {
@Override
public void onSelected(ArrayList<Integer> selectedIds, ArrayList<String> selectedNames, String dataString) {
public void onSelected(List<Integer> selectedIds, List<String> selectedNames, String dataString) {
Log.i("selectedNames", String.valueOf(selectedNames));
@ -167,7 +167,7 @@ public class AddRemoveAssigneesActivity extends BaseActivity {
.multiSelectList(listOfCollaborators)
.onSubmit(new MultiSelectDialog.SubmitCallbackListener() {
@Override
public void onSelected(ArrayList<Integer> selectedIds, ArrayList<String> selectedNames, String dataString) {
public void onSelected(List<Integer> selectedIds, List<String> selectedNames, String dataString) {
updateIssueAssignees(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, loginUid, issueIndex, selectedNames);
tinyDb.putBoolean("singleIssueUpdate", true);
@ -207,17 +207,17 @@ public class AddRemoveAssigneesActivity extends BaseActivity {
}
else if(response.code() == 403) {
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else {
Toasty.info(ctx, getString(R.string.genericError));
Toasty.error(ctx, getString(R.string.genericError));
}
}
@ -254,7 +254,7 @@ public class AddRemoveAssigneesActivity extends BaseActivity {
if(response2.code() == 201) {
Toasty.info(ctx, ctx.getString(R.string.assigneesUpdated));
Toasty.success(ctx, ctx.getString(R.string.assigneesUpdated));
}
else if(response2.code() == 401) {
@ -267,17 +267,17 @@ public class AddRemoveAssigneesActivity extends BaseActivity {
}
else if(response2.code() == 403) {
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response2.code() == 404) {
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else {
Toasty.info(ctx, getString(R.string.genericError));
Toasty.error(ctx, getString(R.string.genericError));
}

View File

@ -1,25 +1,25 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import retrofit2.Call;
import retrofit2.Callback;
import android.content.Context;
import android.graphics.Color;
import android.graphics.drawable.ColorDrawable;
import android.os.Bundle;
import android.util.Log;
import androidx.annotation.NonNull;
import com.google.gson.JsonElement;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.MultiSelectDialog;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.Labels;
import org.mian.gitnex.models.MultiSelectModel;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
@ -128,7 +128,7 @@ public class AddRemoveLabelsActivity extends BaseActivity {
.multiSelectList(listOfLabels)
.onSubmit(new MultiSelectDialog.SubmitCallbackListener() {
@Override
public void onSelected(ArrayList<Integer> selectedIds, ArrayList<String> selectedNames, String dataString) {
public void onSelected(List<Integer> selectedIds, List<String> selectedNames, String dataString) {
String labelIds = selectedIds.toString();
int[] integers;
@ -169,7 +169,7 @@ public class AddRemoveLabelsActivity extends BaseActivity {
.multiSelectList(listOfLabels)
.onSubmit(new MultiSelectDialog.SubmitCallbackListener() {
@Override
public void onSelected(ArrayList<Integer> selectedIds, ArrayList<String> selectedNames, String dataString) {
public void onSelected(List<Integer> selectedIds, List<String> selectedNames, String dataString) {
String labelIds = selectedIds.toString();
int[] integers;
@ -224,17 +224,17 @@ public class AddRemoveLabelsActivity extends BaseActivity {
}
else if(response.code() == 403) {
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else {
Toasty.info(ctx, getString(R.string.genericError));
Toasty.error(ctx, getString(R.string.genericError));
}
}
@ -265,7 +265,7 @@ public class AddRemoveLabelsActivity extends BaseActivity {
if(response.code() == 200) {
Toasty.info(ctx, ctx.getString(R.string.labelsUpdated));
Toasty.success(ctx, ctx.getString(R.string.labelsUpdated));
}
else if(response.code() == 401) {
@ -278,17 +278,17 @@ public class AddRemoveLabelsActivity extends BaseActivity {
}
else if(response.code() == 403) {
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else {
Toasty.info(ctx, getString(R.string.genericError));
Toasty.error(ctx, getString(R.string.genericError));
}

View File

@ -1,13 +1,5 @@
package org.mian.gitnex.activities;
import androidx.annotation.Nullable;
import androidx.appcompat.widget.Toolbar;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout;
import android.content.Context;
import android.content.Intent;
import android.os.Bundle;
@ -19,16 +11,20 @@ import android.view.View;
import android.view.inputmethod.EditorInfo;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.appcompat.widget.SearchView;
import androidx.appcompat.widget.Toolbar;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.AdminGetUsersAdapter;
import org.mian.gitnex.fragments.BottomSheetAdminUsersFragment;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.viewmodels.AdminGetUsersViewModel;
import java.util.List;
import java.util.Objects;
/**
* Author M M Arif
@ -79,18 +75,12 @@ public class AdminGetUsersActivity extends BaseActivity implements BottomSheetAd
DividerItemDecoration.VERTICAL);
mRecyclerView.addItemDecoration(dividerItemDecoration);
swipeRefresh.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
@Override
public void onRefresh() {
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
swipeRefresh.setOnRefreshListener(() -> new Handler().postDelayed(() -> {
swipeRefresh.setRefreshing(false);
AdminGetUsersViewModel.loadUsersList(ctx, instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken));
}
}, 500);
}
});
}, 500));
fetchDataAsync(ctx, instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken));
@ -98,11 +88,10 @@ public class AdminGetUsersActivity extends BaseActivity implements BottomSheetAd
private void fetchDataAsync(Context ctx, String instanceUrl, String instanceToken) {
AdminGetUsersViewModel usersModel = ViewModelProviders.of(this).get(AdminGetUsersViewModel.class);
AdminGetUsersViewModel usersModel = new ViewModelProvider(this).get(AdminGetUsersViewModel.class);
usersModel.getUsersList(ctx, instanceUrl, instanceToken).observe(this, usersListMain -> {
usersModel.getUsersList(ctx, instanceUrl, instanceToken).observe(this, new Observer<List<UserInfo>>() {
@Override
public void onChanged(@Nullable List<UserInfo> usersListMain) {
adapter = new AdminGetUsersAdapter(ctx, usersListMain);
if(adapter.getItemCount() > 0) {
mRecyclerView.setVisibility(View.VISIBLE);
@ -116,7 +105,7 @@ public class AdminGetUsersActivity extends BaseActivity implements BottomSheetAd
mRecyclerView.setVisibility(View.GONE);
noDataUsers.setVisibility(View.VISIBLE);
}
}
});
}
@ -127,17 +116,16 @@ public class AdminGetUsersActivity extends BaseActivity implements BottomSheetAd
final MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.generic_nav_dotted_menu, menu);
new Handler().postDelayed(new Runnable() {
@Override
public void run() {
new Handler().postDelayed(() -> {
if(searchFilter) {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
inflater.inflate(R.menu.search_menu, menu);
MenuItem searchItem = menu.findItem(R.id.action_search);
androidx.appcompat.widget.SearchView searchView = (androidx.appcompat.widget.SearchView) searchItem.getActionView();
SearchView searchView = (SearchView) searchItem.getActionView();
searchView.setImeOptions(EditorInfo.IME_ACTION_DONE);
if(!connToInternet) {
@ -145,19 +133,19 @@ public class AdminGetUsersActivity extends BaseActivity implements BottomSheetAd
}
searchView.setOnQueryTextListener(new androidx.appcompat.widget.SearchView.OnQueryTextListener() {
@Override
public boolean onQueryTextSubmit(String query) {
return true;
}
public boolean onQueryTextSubmit(String query) { return true; }
@Override
public boolean onQueryTextChange(String newText) {
adapter.getFilter().filter(newText);
return false;
}
});
}
}
}, 500);
return true;
@ -194,12 +182,7 @@ public class AdminGetUsersActivity extends BaseActivity implements BottomSheetAd
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
onClickListener = view -> finish();
}
}

View File

@ -1,19 +1,23 @@
package org.mian.gitnex.activities;
import android.content.Context;
import android.os.Bundle;
import androidx.appcompat.app.AppCompatActivity;
import org.acra.ACRA;
import org.acra.BuildConfig;
import org.acra.annotation.AcraCore;
import org.acra.annotation.AcraNotification;
import org.acra.config.CoreConfigurationBuilder;
import org.acra.config.LimiterConfigurationBuilder;
import org.acra.config.MailSenderConfigurationBuilder;
import org.acra.data.StringFormat;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.FontsOverride;
import org.mian.gitnex.helpers.TimeHelper;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.notifications.NotificationsMaster;
import static org.acra.ReportField.*;
/**
* Author M M Arif
@ -23,13 +27,17 @@ import org.mian.gitnex.util.TinyDB;
resTitle = R.string.crashTitle,
resChannelName = R.string.setCrashReports,
resText = R.string.crashMessage)
@AcraCore(reportContent = { ANDROID_VERSION, PHONE_MODEL, STACK_TRACE })
public abstract class BaseActivity extends AppCompatActivity {
private Context appCtx;
@Override
public void onCreate(Bundle savedInstanceState) {
final TinyDB tinyDb = new TinyDB(getApplicationContext());
appCtx = getApplicationContext();
final TinyDB tinyDb = new TinyDB(appCtx);
switch(tinyDb.getInt("themeId")) {
@ -46,6 +54,19 @@ public abstract class BaseActivity extends AppCompatActivity {
}
break;
case 3:
setTheme(R.style.AppThemeRetro);
break;
case 4:
if(TimeHelper.timeBetweenHours(18, 6)) { // 6pm to 6am
setTheme(R.style.AppTheme);
}
else {
setTheme(R.style.AppThemeRetro);
}
break;
default:
setTheme(R.style.AppTheme);
break;
@ -83,6 +104,12 @@ public abstract class BaseActivity extends AppCompatActivity {
}
if(tinyDb.getInt("pollingDelayMinutes") == 0) {
tinyDb.putInt("pollingDelayMinutes", 15);
}
NotificationsMaster.hireWorker(appCtx);
// enabling counter badges by default
if(tinyDb.getString("enableCounterBadgesInit").isEmpty()) {
tinyDb.putBoolean("enableCounterBadges", true);
@ -103,6 +130,12 @@ public abstract class BaseActivity extends AppCompatActivity {
tinyDb.putString("cacheSizeImagesStr", getResources().getString(R.string.cacheSizeImagesSelectionSelectedText));
}
// enable comment drafts by default
if(tinyDb.getString("draftsCommentsDeletionEnabledInit").isEmpty()) {
tinyDb.putBoolean("draftsCommentsDeletionEnabled", true);
tinyDb.putString("draftsCommentsDeletionEnabledInit", "yes");
}
if (tinyDb.getBoolean("crashReportingEnabled")) {
CoreConfigurationBuilder ACRABuilder = new CoreConfigurationBuilder(this);

View File

@ -23,11 +23,10 @@ import org.mian.gitnex.adapters.CommitsAdapter;
import org.mian.gitnex.clients.AppApiService;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.StaticGlobalVariables;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.interfaces.ApiInterface;
import org.mian.gitnex.models.Commits;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import retrofit2.Call;
@ -53,6 +52,7 @@ public class CommitsActivity extends BaseActivity {
private List<Commits> commitsList;
private CommitsAdapter adapter;
private ApiInterface api;
private ProgressBar progressLoadMore;
@Override
protected int getLayoutResourceId() {
@ -85,6 +85,7 @@ public class CommitsActivity extends BaseActivity {
ImageView closeActivity = findViewById(R.id.close);
noData = findViewById(R.id.noDataCommits);
progressLoadMore = findViewById(R.id.progressLoadMore);
progressBar = findViewById(R.id.progress_bar);
SwipeRefreshLayout swipeRefresh = findViewById(R.id.pullToRefresh);
@ -102,7 +103,7 @@ public class CommitsActivity extends BaseActivity {
swipeRefresh.setOnRefreshListener(() -> new Handler().postDelayed(() -> {
swipeRefresh.setRefreshing(false);
loadInitial(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, branchName);
loadInitial(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, branchName, resultLimit);
adapter.notifyDataChanged();
}, 200));
@ -113,7 +114,7 @@ public class CommitsActivity extends BaseActivity {
if(commitsList.size() == resultLimit || pageSize == resultLimit) {
int page = (commitsList.size() + resultLimit) / resultLimit;
loadMore(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, page, branchName);
loadMore(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, page, branchName, resultLimit);
}
@ -124,13 +125,13 @@ public class CommitsActivity extends BaseActivity {
recyclerView.setAdapter(adapter);
api = AppApiService.createService(ApiInterface.class, instanceUrl, ctx);
loadInitial(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, branchName);
loadInitial(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, branchName, resultLimit);
}
private void loadInitial(String token, String repoOwner, String repoName, String branchName) {
private void loadInitial(String token, String repoOwner, String repoName, String branchName, int resultLimit) {
Call<List<Commits>> call = api.getRepositoryCommits(token, repoOwner, repoName, 1, branchName);
Call<List<Commits>> call = api.getRepositoryCommits(token, repoOwner, repoName, 1, branchName, resultLimit);
call.enqueue(new Callback<List<Commits>>() {
@ -175,13 +176,11 @@ public class CommitsActivity extends BaseActivity {
}
private void loadMore(String token, String repoOwner, String repoName, final int page, String branchName) {
private void loadMore(String token, String repoOwner, String repoName, final int page, String branchName, int resultLimit) {
//add loading progress view
commitsList.add(new Commits("load"));
adapter.notifyItemInserted((commitsList.size() - 1));
progressLoadMore.setVisibility(View.VISIBLE);
Call<List<Commits>> call = api.getRepositoryCommits(token, repoOwner, repoName, page, branchName);
Call<List<Commits>> call = api.getRepositoryCommits(token, repoOwner, repoName, page, branchName, resultLimit);
call.enqueue(new Callback<List<Commits>>() {
@ -190,9 +189,6 @@ public class CommitsActivity extends BaseActivity {
if(response.isSuccessful()) {
//remove loading view
commitsList.remove(commitsList.size() - 1);
List<Commits> result = response.body();
assert result != null;
@ -204,12 +200,12 @@ public class CommitsActivity extends BaseActivity {
}
else {
Toasty.info(ctx, getString(R.string.noMoreData));
adapter.setMoreDataAvailable(false);
}
adapter.notifyDataChanged();
progressLoadMore.setVisibility(View.GONE);
}
else {

View File

@ -1,8 +1,6 @@
package org.mian.gitnex.activities;
import android.content.Context;
import android.graphics.PorterDuff;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
@ -19,12 +17,14 @@ import com.google.gson.JsonElement;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.Branches;
import org.mian.gitnex.models.DeleteFile;
import org.mian.gitnex.models.EditFile;
import org.mian.gitnex.models.NewFile;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import retrofit2.Call;
@ -45,8 +45,12 @@ public class CreateFileActivity extends BaseActivity {
private EditText newFileBranchName;
private EditText newFileCommitMessage;
private Spinner newFileBranchesSpinner;
private String filePath;
private String fileSha;
private int fileAction = 0; // 0 = create, 1 = delete, 2 = edit
final Context ctx = this;
private Context appCtx;
private TinyDB tinyDb;
List<Branches> branchesList = new ArrayList<>();
@ -60,12 +64,12 @@ public class CreateFileActivity extends BaseActivity {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
tinyDb = new TinyDB(appCtx);
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
final String loginUid = tinyDb.getString("loginUid");
String repoFullName = tinyDb.getString("repoFullName");
@ -81,6 +85,8 @@ public class CreateFileActivity extends BaseActivity {
newFileCommitMessage = findViewById(R.id.newFileCommitMessage);
TextView branchNameId = findViewById(R.id.branchNameId);
TextView branchNameHintText = findViewById(R.id.branchNameHintText);
TextView toolbarTitle = findViewById(R.id.toolbarTitle);
TextView fileNameHint = findViewById(R.id.fileNameHint);
newFileName.requestFocus();
assert imm != null;
@ -91,11 +97,50 @@ public class CreateFileActivity extends BaseActivity {
newFileCreate = findViewById(R.id.newFileCreate);
if(getIntent().getStringExtra("filePath") != null && getIntent().getIntExtra("fileAction", 1) == 1) {
fileNameHint.setVisibility(View.GONE);
fileAction = getIntent().getIntExtra("fileAction", 1);
filePath = getIntent().getStringExtra("filePath");
String fileContents = getIntent().getStringExtra("fileContents");
fileSha = getIntent().getStringExtra("fileSha");
toolbarTitle.setText(getString(R.string.deleteFileText, filePath));
newFileCreate.setText(R.string.deleteFile);
newFileName.setText(filePath);
newFileName.setEnabled(false);
newFileName.setFocusable(false);
newFileContent.setText(fileContents);
newFileContent.setEnabled(false);
newFileContent.setFocusable(false);
}
if(getIntent().getStringExtra("filePath") != null && getIntent().getIntExtra("fileAction", 2) == 2) {
fileNameHint.setVisibility(View.GONE);
fileAction = getIntent().getIntExtra("fileAction", 2);
filePath = getIntent().getStringExtra("filePath");
String fileContents = getIntent().getStringExtra("fileContents");
fileSha = getIntent().getStringExtra("fileSha");
toolbarTitle.setText(getString(R.string.editFileText, filePath));
newFileCreate.setText(R.string.editFile);
newFileName.setText(filePath);
newFileName.setEnabled(false);
newFileName.setFocusable(false);
newFileContent.setText(fileContents);
}
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
newFileBranchesSpinner = findViewById(R.id.newFileBranchesSpinner);
newFileBranchesSpinner.getBackground().setColorFilter(getResources().getColor(R.color.white), PorterDuff.Mode.SRC_ATOP);
getBranches(instanceUrl, instanceToken, repoOwner, repoName, loginUid);
newFileBranchesSpinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener()
@ -129,15 +174,10 @@ public class CreateFileActivity extends BaseActivity {
if(!connToInternet) {
newFileCreate.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
newFileCreate.setBackground(shape);
} else {
}
else {
newFileCreate.setOnClickListener(createFileListener);
}
}
@ -146,7 +186,7 @@ public class CreateFileActivity extends BaseActivity {
private void processNewFile() {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
AppUtil appUtil = new AppUtil();
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
@ -166,14 +206,14 @@ public class CreateFileActivity extends BaseActivity {
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if(newFileName_.equals("") || newFileContent_.equals("") || newFileCommitMessage_.equals("")) {
Toasty.info(ctx, getString(R.string.newFileRequiredFields));
Toasty.error(ctx, getString(R.string.newFileRequiredFields));
return;
}
@ -181,13 +221,13 @@ public class CreateFileActivity extends BaseActivity {
if(currentBranch.toString().equals("No branch")) {
if(newFileBranchName_.equals("")) {
Toasty.info(ctx, getString(R.string.newFileRequiredFieldNewBranchName));
Toasty.error(ctx, getString(R.string.newFileRequiredFieldNewBranchName));
return;
}
else {
if(!appUtil.checkStringsWithDash(newFileBranchName_)) {
Toasty.info(ctx, getString(R.string.newFileInvalidBranchName));
Toasty.error(ctx, getString(R.string.newFileInvalidBranchName));
return;
}
@ -197,13 +237,28 @@ public class CreateFileActivity extends BaseActivity {
if(appUtil.charactersLength(newFileCommitMessage_) > 255) {
Toasty.info(ctx, getString(R.string.newFileCommitMessageError));
Toasty.warning(ctx, getString(R.string.newFileCommitMessageError));
}
else {
disableProcessButton();
createNewFile(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, newFileName_, appUtil.encodeBase64(newFileContent_), newFileBranchName_, newFileCommitMessage_, currentBranch.toString());
if(fileAction == 1) {
deleteFile(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, filePath,
newFileBranchName_, newFileCommitMessage_, currentBranch.toString(), fileSha);
}
else if(fileAction == 2) {
editFile(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, filePath,
appUtil.encodeBase64(newFileContent_), newFileBranchName_, newFileCommitMessage_, currentBranch.toString(), fileSha);
}
else {
createNewFile(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, newFileName_,
appUtil.encodeBase64(newFileContent_), newFileBranchName_, newFileCommitMessage_, currentBranch.toString());
}
}
@ -232,7 +287,7 @@ public class CreateFileActivity extends BaseActivity {
if(response.code() == 201) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.newFileSuccessMessage));
Toasty.success(ctx, getString(R.string.newFileSuccessMessage));
finish();
}
@ -249,11 +304,11 @@ public class CreateFileActivity extends BaseActivity {
if(response.code() == 404) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.apiNotFound));
Toasty.warning(ctx, getString(R.string.apiNotFound));
}
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.orgCreatedError));
Toasty.error(ctx, getString(R.string.orgCreatedError));
}
}
@ -262,6 +317,150 @@ public class CreateFileActivity extends BaseActivity {
@Override
public void onFailure(@NonNull Call<JsonElement> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
enableProcessButton();
}
});
}
private void deleteFile(final String instanceUrl, final String token, String repoOwner, String repoName, String fileName, String fileBranchName, String fileCommitMessage, String currentBranch, String fileSha) {
String branchName;
DeleteFile deleteFileJsonStr;
if(currentBranch.equals("No branch")) {
branchName = fileBranchName;
deleteFileJsonStr = new DeleteFile("", fileCommitMessage, fileBranchName, fileSha);
}
else {
branchName = currentBranch;
deleteFileJsonStr = new DeleteFile(currentBranch, fileCommitMessage, "", fileSha);
}
Call<JsonElement> call = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.deleteFile(token, repoOwner, repoName, fileName, deleteFileJsonStr);
call.enqueue(new Callback<JsonElement>() {
@Override
public void onResponse(@NonNull Call<JsonElement> call, @NonNull retrofit2.Response<JsonElement> response) {
if(response.code() == 200) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.deleteFileMessage, branchName));
getIntent().removeExtra("filePath");
getIntent().removeExtra("fileSha");
getIntent().removeExtra("fileContents");
finish();
}
else if(response.code() == 401) {
enableProcessButton();
AlertDialogs.authorizationTokenRevokedDialog(ctx, getResources().getString(R.string.alertDialogTokenRevokedTitle),
getResources().getString(R.string.alertDialogTokenRevokedMessage),
getResources().getString(R.string.alertDialogTokenRevokedCopyNegativeButton),
getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
}
else {
if(response.code() == 404) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.apiNotFound));
}
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.genericError));
}
}
}
@Override
public void onFailure(@NonNull Call<JsonElement> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
enableProcessButton();
}
});
}
private void editFile(final String instanceUrl, final String token, String repoOwner, String repoName, String fileName, String fileContent, String fileBranchName, String fileCommitMessage, String currentBranch, String fileSha) {
String branchName;
EditFile editFileJsonStr;
if(currentBranch.equals("No branch")) {
branchName = fileBranchName;
editFileJsonStr = new EditFile("", fileCommitMessage, fileBranchName, fileSha, fileContent);
}
else {
branchName = currentBranch;
editFileJsonStr = new EditFile(currentBranch, fileCommitMessage, "", fileSha, fileContent);
}
Call<JsonElement> call = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.editFile(token, repoOwner, repoName, fileName, editFileJsonStr);
call.enqueue(new Callback<JsonElement>() {
@Override
public void onResponse(@NonNull Call<JsonElement> call, @NonNull retrofit2.Response<JsonElement> response) {
if(response.code() == 200) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.editFileMessage, branchName));
getIntent().removeExtra("filePath");
getIntent().removeExtra("fileSha");
getIntent().removeExtra("fileContents");
tinyDb.putBoolean("fileModified", true);
finish();
}
else if(response.code() == 401) {
enableProcessButton();
AlertDialogs.authorizationTokenRevokedDialog(ctx, getResources().getString(R.string.alertDialogTokenRevokedTitle),
getResources().getString(R.string.alertDialogTokenRevokedMessage),
getResources().getString(R.string.alertDialogTokenRevokedCopyNegativeButton),
getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
}
else {
if(response.code() == 404) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.apiNotFound));
}
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.genericError));
}
}
}
@Override
public void onFailure(@NonNull Call<JsonElement> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
enableProcessButton();
}
@ -326,21 +525,11 @@ public class CreateFileActivity extends BaseActivity {
private void disableProcessButton() {
newFileCreate.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
newFileCreate.setBackground(shape);
}
private void enableProcessButton() {
newFileCreate.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
newFileCreate.setBackground(shape);
}
}

View File

@ -1,13 +1,7 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import android.app.DatePickerDialog;
import android.content.Context;
import android.graphics.PorterDuff;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
@ -19,6 +13,7 @@ import android.widget.EditText;
import android.widget.ImageView;
import android.widget.Spinner;
import android.widget.TextView;
import androidx.annotation.NonNull;
import com.google.gson.JsonElement;
import com.hendraanggrian.appcompat.socialview.Mention;
import com.hendraanggrian.appcompat.widget.MentionArrayAdapter;
@ -26,22 +21,25 @@ import com.hendraanggrian.appcompat.widget.SocialAutoCompleteTextView;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.MultiSelectDialog;
import org.mian.gitnex.helpers.StaticGlobalVariables;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.Collaborators;
import org.mian.gitnex.models.CreateIssue;
import org.mian.gitnex.models.Labels;
import org.mian.gitnex.models.Milestones;
import org.mian.gitnex.models.MultiSelectModel;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Calendar;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
/**
* Author M M Arif
@ -82,7 +80,7 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
@ -96,8 +94,9 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
final String repoName = parts[1];
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
// if gitea is 1.12 or higher use the new limit
// require gitea 1.12 or higher
if(new Version(tinyDb.getString("giteaVersion")).higherOrEqual("1.12.0")) {
resultLimit = StaticGlobalVariables.resultLimitNewGiteaInstances;
}
@ -127,7 +126,6 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
newIssueDueDate.setOnClickListener(this);
newIssueMilestoneSpinner = findViewById(R.id.newIssueMilestoneSpinner);
newIssueMilestoneSpinner.getBackground().setColorFilter(getResources().getColor(R.color.white), PorterDuff.Mode.SRC_ATOP);
getMilestones(instanceUrl, instanceToken, repoOwner, repoName, loginUid, resultLimit);
getLabels(instanceUrl, instanceToken, repoOwner, repoName, loginUid);
@ -138,22 +136,17 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
if(!connToInternet) {
createNewIssueButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createNewIssueButton.setBackground(shape);
} else {
}
else {
createNewIssueButton.setOnClickListener(this);
}
}
private void processNewIssue() {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
final String loginUid = tinyDb.getString("loginUid");
@ -175,21 +168,21 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if (newIssueTitleForm.equals("")) {
Toasty.info(ctx, getString(R.string.issueTitleEmpty));
Toasty.error(ctx, getString(R.string.issueTitleEmpty));
return;
}
/*if (newIssueDescriptionForm.equals("")) {
Toasty.info(ctx, getString(R.string.issueDescriptionEmpty));
Toasty.error(ctx, getString(R.string.issueDescriptionEmpty));
return;
}*/
@ -207,9 +200,9 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
}
int[] integers;
if (!newIssueLabelsIdHolderForm.equals("")) {
if (!newIssueLabelsIdHolderForm.equals("") && !newIssueLabelsIdHolderForm.equals("[]")) {
String[] items = newIssueLabelsIdHolderForm.replaceAll("\\[", "").replaceAll("\\]", "").replaceAll("\\s", "").split(",");
String[] items = newIssueLabelsIdHolderForm.replaceAll("\\[", "").replaceAll("]", "").replaceAll("\\s", "").split(",");
integers = new int[items.length];
for (int i = 0; i < integers.length; i++) {
integers[i] = Integer.parseInt(items[i]);
@ -299,7 +292,7 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
TinyDB tinyDb = new TinyDB(appCtx);
tinyDb.putBoolean("resumeIssues", true);
Toasty.info(ctx, getString(R.string.issueCreated));
Toasty.success(ctx, getString(R.string.issueCreated));
enableProcessButton();
finish();
@ -317,7 +310,7 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
}
else {
Toasty.info(ctx, getString(R.string.issueCreatedError));
Toasty.error(ctx, getString(R.string.issueCreatedError));
enableProcessButton();
//Log.i("isSuccessful2", String.valueOf(response2.body()));
@ -335,12 +328,8 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
onClickListener = view -> finish();
}
private void getMilestones(String instanceUrl, String instanceToken, String repoOwner, String repoName, String loginUid, int resultLimit) {
@ -444,7 +433,7 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
.multiSelectList(listOfAssignees)
.onSubmit(new MultiSelectDialog.SubmitCallbackListener() {
@Override
public void onSelected(ArrayList<Integer> selectedIds, ArrayList<String> selectedNames, String dataString) {
public void onSelected(List<Integer> selectedIds, List<String> selectedNames, String dataString) {
assigneesList.setText(dataString);
@ -507,7 +496,7 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
.multiSelectList(listOfLabels)
.onSubmit(new MultiSelectDialog.SubmitCallbackListener() {
@Override
public void onSelected(ArrayList<Integer> selectedIds, ArrayList<String> selectedNames, String dataString) {
public void onSelected(List<Integer> selectedIds, List<String> selectedNames, String dataString) {
newIssueLabels.setText(dataString.trim());
labelsIdHolder.setText(selectedIds.toString());
@ -541,7 +530,7 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
multiSelectDialog.show(getSupportFragmentManager(), "multiSelectDialog");
}
else {
Toasty.info(ctx, getResources().getString(R.string.noAssigneesFound));
Toasty.warning(ctx, getResources().getString(R.string.noAssigneesFound));
}
}
else if (v == newIssueLabels) {
@ -549,7 +538,7 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
multiSelectDialogLabels.show(getSupportFragmentManager(), "multiSelectDialogLabels");
}
else {
Toasty.info(ctx, getResources().getString(R.string.noLabelsFound));
Toasty.warning(ctx, getResources().getString(R.string.noLabelsFound));
}
}
else if (v == newIssueDueDate) {
@ -581,20 +570,10 @@ public class CreateIssueActivity extends BaseActivity implements View.OnClickLis
private void disableProcessButton() {
createNewIssueButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createNewIssueButton.setBackground(shape);
}
private void enableProcessButton() {
createNewIssueButton.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
createNewIssueButton.setBackground(shape);
}
}

View File

@ -1,13 +1,7 @@
package org.mian.gitnex.activities;
import androidx.annotation.ColorInt;
import androidx.annotation.NonNull;
import androidx.core.content.ContextCompat;
import retrofit2.Call;
import retrofit2.Callback;
import android.content.Context;
import android.graphics.Color;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
@ -16,19 +10,24 @@ import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.annotation.ColorInt;
import androidx.annotation.NonNull;
import androidx.core.content.ContextCompat;
import com.pes.androidmaterialcolorpickerdialog.ColorPicker;
import com.pes.androidmaterialcolorpickerdialog.ColorPickerCallback;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.CreateLabel;
import org.mian.gitnex.models.Labels;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.viewmodels.LabelsViewModel;
import java.util.Objects;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
@ -73,7 +72,7 @@ public class CreateLabelActivity extends BaseActivity {
}
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
ImageView closeActivity = findViewById(R.id.close);
colorPicker = findViewById(R.id.colorPicker);
@ -118,43 +117,28 @@ public class CreateLabelActivity extends BaseActivity {
createLabelButton.setText(getResources().getString(R.string.newUpdateButtonCopy));
createLabelButton.setOnClickListener(updateLabelListener);
return;
}
if(!connToInternet) {
createLabelButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createLabelButton.setBackground(shape);
} else {
}
else {
createLabelButton.setOnClickListener(createLabelListener);
}
}
private View.OnClickListener createLabelListener = new View.OnClickListener() {
public void onClick(View v) {
processCreateLabel();
}
};
private View.OnClickListener createLabelListener = v -> processCreateLabel();
private View.OnClickListener updateLabelListener = new View.OnClickListener() {
public void onClick(View v) {
processUpdateLabel();
}
};
private View.OnClickListener updateLabelListener = v -> processUpdateLabel();
private void processUpdateLabel() {
final TinyDB tinyDb = new TinyDB(appCtx);
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
AppUtil appUtil = new AppUtil();
String repoFullName = tinyDb.getString("repoFullName");
String[] parts = repoFullName.split("/");
@ -176,33 +160,34 @@ public class CreateLabelActivity extends BaseActivity {
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if(updateLabelName.equals("")) {
Toasty.info(ctx, getString(R.string.labelEmptyError));
Toasty.error(ctx, getString(R.string.labelEmptyError));
return;
}
if(!appUtil.checkStrings(updateLabelName)) {
Toasty.info(ctx, getString(R.string.labelNameError));
Toasty.error(ctx, getString(R.string.labelNameError));
return;
}
disableProcessButton();
patchLabel(instanceUrl, instanceToken, repoOwner, repoName, updateLabelName, updateLabelColor, Integer.valueOf(getIntent().getStringExtra("labelId")), loginUid);
patchLabel(instanceUrl, instanceToken, repoOwner, repoName, updateLabelName, updateLabelColor, Integer.parseInt(
Objects.requireNonNull(getIntent().getStringExtra("labelId"))), loginUid);
}
private void processCreateLabel() {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
AppUtil appUtil = new AppUtil();
TinyDB tinyDb = new TinyDB(appCtx);
String repoFullName = tinyDb.getString("repoFullName");
@ -224,21 +209,21 @@ public class CreateLabelActivity extends BaseActivity {
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if(newLabelName.equals("")) {
Toasty.info(ctx, getString(R.string.labelEmptyError));
Toasty.error(ctx, getString(R.string.labelEmptyError));
return;
}
if(!appUtil.checkStrings(newLabelName)) {
Toasty.info(ctx, getString(R.string.labelNameError));
Toasty.error(ctx, getString(R.string.labelNameError));
return;
}
@ -267,7 +252,7 @@ public class CreateLabelActivity extends BaseActivity {
if(response.code() == 201) {
Toasty.info(ctx, getString(R.string.labelCreated));
Toasty.success(ctx, getString(R.string.labelCreated));
tinyDb.putString("labelColor", "");
tinyDb.putBoolean("labelsRefresh", true);
finish();
@ -286,7 +271,7 @@ public class CreateLabelActivity extends BaseActivity {
enableProcessButton();
tinyDb.putString("labelColor", "");
Toasty.info(ctx, getString(R.string.labelGeneralError));
Toasty.error(ctx, getString(R.string.labelGeneralError));
}
@ -294,6 +279,7 @@ public class CreateLabelActivity extends BaseActivity {
@Override
public void onFailure(@NonNull Call<CreateLabel> call, @NonNull Throwable t) {
tinyDb.putString("labelColor", "");
Log.e("onFailure", t.toString());
enableProcessButton();
@ -322,7 +308,7 @@ public class CreateLabelActivity extends BaseActivity {
if(response.isSuccessful()) {
if(response.code() == 200) {
Toasty.info(ctx, getString(R.string.labelUpdated));
Toasty.success(ctx, getString(R.string.labelUpdated));
tinyDb.putString("labelColor", "");
tinyDb.putBoolean("labelsRefresh", true);
tinyDb.putString("labelColorDefault", "");
@ -348,7 +334,7 @@ public class CreateLabelActivity extends BaseActivity {
enableProcessButton();
tinyDb.putString("labelColor", "");
tinyDb.putString("labelColorDefault", "");
Toasty.info(ctx, getString(R.string.labelGeneralError));
Toasty.error(ctx, getString(R.string.labelGeneralError));
}
@ -356,6 +342,7 @@ public class CreateLabelActivity extends BaseActivity {
@Override
public void onFailure(@NonNull Call<CreateLabel> call, @NonNull Throwable t) {
tinyDb.putString("labelColor", "");
tinyDb.putString("labelColorDefault", "");
Log.e("onFailure", t.toString());
@ -395,7 +382,7 @@ public class CreateLabelActivity extends BaseActivity {
if(response.isSuccessful()) {
if(response.code() == 204) {
Toasty.info(ctx, getString(R.string.labelDeleteText));
Toasty.success(ctx, getString(R.string.labelDeleteText));
LabelsViewModel.loadLabelsList(instanceUrl, instanceToken, repoOwner, repoName, ctx);
getIntent().removeExtra("labelAction");
getIntent().removeExtra("labelId");
@ -412,7 +399,7 @@ public class CreateLabelActivity extends BaseActivity {
}
else {
Toasty.info(ctx, getString(R.string.labelDeleteErrorText));
Toasty.error(ctx, getString(R.string.labelDeleteErrorText));
}
@ -429,21 +416,11 @@ public class CreateLabelActivity extends BaseActivity {
private void disableProcessButton() {
createLabelButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createLabelButton.setBackground(shape);
}
private void enableProcessButton() {
createLabelButton.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
createLabelButton.setBackground(shape);
}
}

View File

@ -1,11 +1,7 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import retrofit2.Call;
import retrofit2.Callback;
import android.app.DatePickerDialog;
import android.content.Context;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
@ -14,16 +10,19 @@ import android.widget.Button;
import android.widget.DatePicker;
import android.widget.EditText;
import android.widget.ImageView;
import androidx.annotation.NonNull;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.Milestones;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.Calendar;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
@ -50,7 +49,7 @@ public class CreateMilestoneActivity extends BaseActivity implements View.OnClic
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
@ -71,28 +70,19 @@ public class CreateMilestoneActivity extends BaseActivity implements View.OnClic
if(!connToInternet) {
createNewMilestoneButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createNewMilestoneButton.setBackground(shape);
} else {
}
else {
createNewMilestoneButton.setOnClickListener(createMilestoneListener);
}
}
private View.OnClickListener createMilestoneListener = new View.OnClickListener() {
public void onClick(View v) {
processNewMilestone();
}
};
private View.OnClickListener createMilestoneListener = v -> processNewMilestone();
private void processNewMilestone() {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
AppUtil appUtil = new AppUtil();
TinyDB tinyDb = new TinyDB(appCtx);
String repoFullName = tinyDb.getString("repoFullName");
@ -110,14 +100,14 @@ public class CreateMilestoneActivity extends BaseActivity implements View.OnClic
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if(newMilestoneTitle.equals("")) {
Toasty.info(ctx, getString(R.string.milestoneNameErrorEmpty));
Toasty.error(ctx, getString(R.string.milestoneNameErrorEmpty));
return;
}
@ -125,7 +115,7 @@ public class CreateMilestoneActivity extends BaseActivity implements View.OnClic
if(!newMilestoneDescription.equals("")) {
if (appUtil.charactersLength(newMilestoneDescription) > 255) {
Toasty.info(ctx, getString(R.string.milestoneDescError));
Toasty.warning(ctx, getString(R.string.milestoneDescError));
return;
}
@ -133,10 +123,13 @@ public class CreateMilestoneActivity extends BaseActivity implements View.OnClic
String finalMilestoneDueDate = null;
if(!newMilestoneDueDate.isEmpty()) {
finalMilestoneDueDate = (AppUtil.customDateCombine(AppUtil.customDateFormat(newMilestoneDueDate)));
} else if (new Version(tinyDb.getString("giteaVersion")).less("1.10.0")) {
}
else if (new Version(tinyDb.getString("giteaVersion")).less("1.10.0")) {
// if Gitea version is less than 1.10.0 DueDate is required
Toasty.info(ctx, getString(R.string.milestoneDateEmpty));
Toasty.warning(ctx, getString(R.string.milestoneDateEmpty));
return;
}
@ -166,7 +159,7 @@ public class CreateMilestoneActivity extends BaseActivity implements View.OnClic
TinyDB tinyDb = new TinyDB(appCtx);
tinyDb.putBoolean("milestoneCreated", true);
Toasty.info(ctx, getString(R.string.milestoneCreated));
Toasty.success(ctx, getString(R.string.milestoneCreated));
enableProcessButton();
finish();
@ -184,7 +177,7 @@ public class CreateMilestoneActivity extends BaseActivity implements View.OnClic
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.milestoneCreatedError));
Toasty.error(ctx, getString(R.string.milestoneCreatedError));
}
@ -226,32 +219,18 @@ public class CreateMilestoneActivity extends BaseActivity implements View.OnClic
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
onClickListener = view -> finish();
}
private void disableProcessButton() {
createNewMilestoneButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createNewMilestoneButton.setBackground(shape);
}
private void enableProcessButton() {
createNewMilestoneButton.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
createNewMilestoneButton.setBackground(shape);
}
}

View File

@ -1,10 +1,6 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import retrofit2.Call;
import retrofit2.Callback;
import android.content.Context;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import android.util.Log;
import android.util.Patterns;
@ -13,14 +9,17 @@ import android.view.inputmethod.InputMethodManager;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import androidx.annotation.NonNull;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
@ -48,7 +47,7 @@ public class CreateNewUserActivity extends BaseActivity {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
@ -69,18 +68,17 @@ public class CreateNewUserActivity extends BaseActivity {
if(!connToInternet) {
disableProcessButton();
} else {
}
else {
createUserButton.setOnClickListener(createNewUserListener);
}
}
private void processCreateNewUser() {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
AppUtil appUtil = new AppUtil();
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
@ -94,35 +92,35 @@ public class CreateNewUserActivity extends BaseActivity {
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if(newFullName.equals("") || newUserName.equals("") | newUserEmail.equals("") || newUserPassword.equals("")) {
Toasty.info(ctx, getString(R.string.emptyFields));
Toasty.error(ctx, getString(R.string.emptyFields));
return;
}
if(!appUtil.checkStrings(newFullName)) {
Toasty.info(ctx, getString(R.string.userInvalidFullName));
Toasty.error(ctx, getString(R.string.userInvalidFullName));
return;
}
if(!appUtil.checkStringsWithAlphaNumeric(newUserName)) {
Toasty.info(ctx, getString(R.string.userInvalidUserName));
Toasty.error(ctx, getString(R.string.userInvalidUserName));
return;
}
if(!Patterns.EMAIL_ADDRESS.matcher(newUserEmail).matches()) {
Toasty.info(ctx, getString(R.string.userInvalidEmail));
Toasty.error(ctx, getString(R.string.userInvalidEmail));
return;
}
@ -150,7 +148,7 @@ public class CreateNewUserActivity extends BaseActivity {
if(response.code() == 201) {
Toasty.info(ctx, getString(R.string.userCreatedText));
Toasty.success(ctx, getString(R.string.userCreatedText));
enableProcessButton();
finish();
@ -167,25 +165,25 @@ public class CreateNewUserActivity extends BaseActivity {
else if(response.code() == 403) {
enableProcessButton();
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
enableProcessButton();
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else if(response.code() == 422) {
enableProcessButton();
Toasty.info(ctx, ctx.getString(R.string.userExistsError));
Toasty.warning(ctx, ctx.getString(R.string.userExistsError));
}
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.genericError));
Toasty.error(ctx, getString(R.string.genericError));
}
@ -193,6 +191,7 @@ public class CreateNewUserActivity extends BaseActivity {
@Override
public void onFailure(@NonNull Call<UserInfo> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
enableProcessButton();
}
@ -200,39 +199,21 @@ public class CreateNewUserActivity extends BaseActivity {
}
private View.OnClickListener createNewUserListener = new View.OnClickListener() {
public void onClick(View v) {
processCreateNewUser();
}
};
private View.OnClickListener createNewUserListener = v -> processCreateNewUser();
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
onClickListener = view -> finish();
}
private void disableProcessButton() {
createUserButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createUserButton.setBackground(shape);
}
private void enableProcessButton() {
createUserButton.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
createUserButton.setBackground(shape);
}
}

View File

@ -1,23 +1,22 @@
package org.mian.gitnex.activities;
import android.content.Context;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import androidx.annotation.NonNull;
import android.util.Log;
import android.view.View;
import android.view.inputmethod.InputMethodManager;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import androidx.annotation.NonNull;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.UserOrganizations;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import retrofit2.Call;
import retrofit2.Callback;
@ -47,7 +46,7 @@ public class CreateOrganizationActivity extends BaseActivity {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
@ -67,15 +66,10 @@ public class CreateOrganizationActivity extends BaseActivity {
if(!connToInternet) {
createOrganizationButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createOrganizationButton.setBackground(shape);
} else {
}
else {
createOrganizationButton.setOnClickListener(createOrgListener);
}
}
@ -97,7 +91,7 @@ public class CreateOrganizationActivity extends BaseActivity {
private void processNewOrganization() {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
AppUtil appUtil = new AppUtil();
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
@ -109,7 +103,7 @@ public class CreateOrganizationActivity extends BaseActivity {
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
@ -117,7 +111,7 @@ public class CreateOrganizationActivity extends BaseActivity {
if(!newOrgDesc.equals("")) {
if (appUtil.charactersLength(newOrgDesc) > 255) {
Toasty.info(ctx, getString(R.string.orgDescError));
Toasty.warning(ctx, getString(R.string.orgDescError));
return;
}
@ -125,12 +119,12 @@ public class CreateOrganizationActivity extends BaseActivity {
if(newOrgName.equals("")) {
Toasty.info(ctx, getString(R.string.orgNameErrorEmpty));
Toasty.error(ctx, getString(R.string.orgNameErrorEmpty));
}
else if(!appUtil.checkStrings(newOrgName)) {
Toasty.info(ctx, getString(R.string.orgNameErrorInvalid));
Toasty.warning(ctx, getString(R.string.orgNameErrorInvalid));
}
else {
@ -161,7 +155,7 @@ public class CreateOrganizationActivity extends BaseActivity {
TinyDB tinyDb = new TinyDB(appCtx);
tinyDb.putBoolean("orgCreated", true);
enableProcessButton();
Toasty.info(ctx, getString(R.string.orgCreated));
Toasty.success(ctx, getString(R.string.orgCreated));
finish();
}
@ -177,24 +171,24 @@ public class CreateOrganizationActivity extends BaseActivity {
else if(response.code() == 409) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.orgExistsError));
Toasty.warning(ctx, getString(R.string.orgExistsError));
}
else if(response.code() == 422) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.orgExistsError));
Toasty.warning(ctx, getString(R.string.orgExistsError));
}
else {
if(response.code() == 404) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.apiNotFound));
Toasty.warning(ctx, getString(R.string.apiNotFound));
}
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.orgCreatedError));
Toasty.error(ctx, getString(R.string.orgCreatedError));
}
}
@ -213,21 +207,11 @@ public class CreateOrganizationActivity extends BaseActivity {
private void disableProcessButton() {
createOrganizationButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createOrganizationButton.setBackground(shape);
}
private void enableProcessButton() {
createOrganizationButton.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
createOrganizationButton.setBackground(shape);
}
}

View File

@ -0,0 +1,431 @@
package org.mian.gitnex.activities;
import android.app.DatePickerDialog;
import android.app.Dialog;
import android.content.Context;
import android.graphics.Color;
import android.graphics.drawable.ColorDrawable;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.ArrayAdapter;
import android.widget.ImageView;
import androidx.annotation.NonNull;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.LabelsListAdapter;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.databinding.ActivityCreatePrBinding;
import org.mian.gitnex.databinding.CustomLabelsSelectionDialogBinding;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.StaticGlobalVariables;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.Branches;
import org.mian.gitnex.models.CreatePullRequest;
import org.mian.gitnex.models.Labels;
import org.mian.gitnex.models.Milestones;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.List;
import okhttp3.ResponseBody;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
*/
public class CreatePullRequestActivity extends BaseActivity implements LabelsListAdapter.LabelsListAdapterListener {
private View.OnClickListener onClickListener;
private Context ctx = this;
private Context appCtx;
private TinyDB tinyDb;
private ActivityCreatePrBinding viewBinding;
private CustomLabelsSelectionDialogBinding labelsBinding;
private int resultLimit = StaticGlobalVariables.resultLimitOldGiteaInstances;
private Dialog dialogLabels;
private String labelsSetter;
private ArrayList<Integer> labelsIds = new ArrayList<>();
private ArrayList<String> assignees = new ArrayList<>();
private int milestoneId;
private String instanceUrl;
private String loginUid;
private String instanceToken;
private String repoOwner;
private String repoName;
private LabelsListAdapter labelsAdapter;
List<Milestones> milestonesList = new ArrayList<>();
List<Branches> branchesList = new ArrayList<>();
List<Labels> labelsList = new ArrayList<>();
public CreatePullRequestActivity() {
}
@Override
protected int getLayoutResourceId(){
return R.layout.activity_create_pr;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
tinyDb = new TinyDB(appCtx);
viewBinding = ActivityCreatePrBinding.inflate(getLayoutInflater());
View view = viewBinding.getRoot();
setContentView(view);
instanceUrl = tinyDb.getString("instanceUrl");
loginUid = tinyDb.getString("loginUid");
String repoFullName = tinyDb.getString("repoFullName");
String[] parts = repoFullName.split("/");
repoOwner = parts[0];
repoName = parts[1];
instanceToken = "token " + tinyDb.getString(loginUid + "-token");
// require gitea 1.12 or higher
if(new Version(tinyDb.getString("giteaVersion")).higherOrEqual("1.12.0")) {
resultLimit = StaticGlobalVariables.resultLimitNewGiteaInstances;
}
labelsAdapter = new LabelsListAdapter(labelsList, CreatePullRequestActivity.this);
ImageView closeActivity = findViewById(R.id.close);
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
viewBinding.prDueDate.setOnClickListener(dueDate ->
setDueDate()
);
disableProcessButton();
getMilestones(instanceUrl, instanceToken, repoOwner, repoName, loginUid, resultLimit);
getBranches(instanceUrl, instanceToken, repoOwner, repoName, loginUid);
viewBinding.prLabels.setOnClickListener(prLabels ->
showLabels()
);
viewBinding.createPr.setOnClickListener(createPr ->
processPullRequest()
);
}
private void processPullRequest() {
String prTitle = String.valueOf(viewBinding.prTitle.getText());
String prDescription = String.valueOf(viewBinding.prBody.getText());
String mergeInto = viewBinding.mergeIntoBranchSpinner.getText().toString();
String pullFrom = viewBinding.pullFromBranchSpinner.getText().toString();
String dueDate = String.valueOf(viewBinding.prDueDate.getText());
assignees.add("");
if (labelsIds.size() == 0) {
labelsIds.add(0);
}
if (dueDate.matches("")) {
dueDate = null;
}
else {
dueDate = AppUtil.customDateCombine(AppUtil.customDateFormat(dueDate));
}
if(prTitle.matches("")) {
Toasty.error(ctx, getString(R.string.titleError));
}
else if(mergeInto.matches("")) {
Toasty.error(ctx, getString(R.string.mergeIntoError));
}
else if(pullFrom.matches("")) {
Toasty.error(ctx, getString(R.string.pullFromError));
}
else if(pullFrom.equals(mergeInto)) {
Toasty.error(ctx, getString(R.string.sameBranchesError));
}
else {
createPullRequest(prTitle, prDescription, mergeInto, pullFrom, milestoneId, dueDate, assignees);
}
//Log.e("processPullRequest", String.valueOf(milestoneId));
}
private void createPullRequest(String prTitle, String prDescription, String mergeInto, String pullFrom, int milestoneId, String dueDate, ArrayList<String> assignees) {
CreatePullRequest createPullRequest = new CreatePullRequest(prTitle, prDescription, loginUid, mergeInto, pullFrom, milestoneId, dueDate, assignees, labelsIds);
Call<ResponseBody> transferCall = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.createPullRequest(instanceToken, repoOwner, repoName, createPullRequest);
transferCall.enqueue(new Callback<ResponseBody>() {
@Override
public void onResponse(@NonNull Call<ResponseBody> call, @NonNull retrofit2.Response<ResponseBody> response) {
disableProcessButton();
if (response.code() == 201) {
Toasty.success(ctx, getString(R.string.prCreateSuccess));
finish();
}
else if (response.code() == 409 && response.message().equals("Conflict")) {
enableProcessButton();
Toasty.error(ctx, getString(R.string.prAlreadyExists));
}
else if (response.code() == 404) {
enableProcessButton();
Toasty.error(ctx, getString(R.string.apiNotFound));
}
else {
enableProcessButton();
Toasty.error(ctx, getString(R.string.genericError));
}
}
@Override
public void onFailure(@NonNull Call<ResponseBody> call, @NonNull Throwable t) {
enableProcessButton();
Toasty.error(ctx, getString(R.string.genericServerResponseError));
}
});
}
@Override
public void labelsStringData(ArrayList<String> data) {
labelsSetter = String.valueOf(data);
viewBinding.prLabels.setText(labelsSetter.replace("]", "").replace("[", ""));
}
@Override
public void labelsIdsData(ArrayList<Integer> data) {
labelsIds = data;
}
private void showLabels() {
dialogLabels = new Dialog(ctx, R.style.ThemeOverlay_MaterialComponents_Dialog_Alert);
if (dialogLabels.getWindow() != null) {
dialogLabels.getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
}
labelsBinding = CustomLabelsSelectionDialogBinding.inflate(LayoutInflater.from(ctx));
View view = labelsBinding.getRoot();
dialogLabels.setContentView(view);
labelsBinding.cancel.setOnClickListener(editProperties ->
dialogLabels.dismiss()
);
Call<List<Labels>> call = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.getlabels(instanceToken, repoOwner, repoName);
call.enqueue(new Callback<List<Labels>>() {
@Override
public void onResponse(@NonNull Call<List<Labels>> call, @NonNull retrofit2.Response<List<Labels>> response) {
labelsList.clear();
List<Labels> labelsList_ = response.body();
labelsBinding.progressBar.setVisibility(View.GONE);
labelsBinding.dialogFrame.setVisibility(View.VISIBLE);
if (response.code() == 200) {
assert labelsList_ != null;
if(labelsList_.size() > 0) {
for (int i = 0; i < labelsList_.size(); i++) {
labelsList.add(new Labels(labelsList_.get(i).getId(), labelsList_.get(i).getName()));
}
}
else {
dialogLabels.dismiss();
Toasty.warning(ctx, getString(R.string.noLabelsFound));
}
labelsBinding.labelsRecyclerView.setAdapter(labelsAdapter);
}
else {
Toasty.error(ctx, getString(R.string.genericError));
}
}
@Override
public void onFailure(@NonNull Call<List<Labels>> call, @NonNull Throwable t) {
Toasty.error(ctx, getString(R.string.genericServerResponseError));
}
});
dialogLabels.show();
}
private void getBranches(String instanceUrl, String instanceToken, String repoOwner, String repoName, String loginUid) {
Call<List<Branches>> call = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.getBranches(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName);
call.enqueue(new Callback<List<Branches>>() {
@Override
public void onResponse(@NonNull Call<List<Branches>> call, @NonNull retrofit2.Response<List<Branches>> response) {
if(response.isSuccessful()) {
if(response.code() == 200) {
List<Branches> branchesList_ = response.body();
assert branchesList_ != null;
if(branchesList_.size() > 0) {
for (int i = 0; i < branchesList_.size(); i++) {
Branches data = new Branches(
branchesList_.get(i).getName()
);
branchesList.add(data);
}
}
ArrayAdapter<Branches> adapter = new ArrayAdapter<>(CreatePullRequestActivity.this,
R.layout.list_spinner_items, branchesList);
viewBinding.mergeIntoBranchSpinner.setAdapter(adapter);
viewBinding.pullFromBranchSpinner.setAdapter(adapter);
enableProcessButton();
}
}
}
@Override
public void onFailure(@NonNull Call<List<Branches>> call, @NonNull Throwable t) {
Toasty.error(ctx, getString(R.string.genericServerResponseError));
}
});
}
private void getMilestones(String instanceUrl, String instanceToken, String repoOwner, String repoName, String loginUid, int resultLimit) {
String msState = "open";
Call<List<Milestones>> call = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.getMilestones(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, 1, resultLimit, msState);
call.enqueue(new Callback<List<Milestones>>() {
@Override
public void onResponse(@NonNull Call<List<Milestones>> call, @NonNull retrofit2.Response<List<Milestones>> response) {
if(response.code() == 200) {
List<Milestones> milestonesList_ = response.body();
milestonesList.add(new Milestones(0,getString(R.string.issueCreatedNoMilestone)));
assert milestonesList_ != null;
if(milestonesList_.size() > 0) {
for (int i = 0; i < milestonesList_.size(); i++) {
//Don't translate "open" is a enum
if(milestonesList_.get(i).getState().equals("open")) {
Milestones data = new Milestones(
milestonesList_.get(i).getId(),
milestonesList_.get(i).getTitle()
);
milestonesList.add(data);
}
}
}
ArrayAdapter<Milestones> adapter = new ArrayAdapter<>(CreatePullRequestActivity.this,
R.layout.list_spinner_items, milestonesList);
viewBinding.milestonesSpinner.setAdapter(adapter);
enableProcessButton();
viewBinding.milestonesSpinner.setOnItemClickListener ((parent, view, position, id) ->
milestoneId = milestonesList.get(position).getId()
);
}
}
@Override
public void onFailure(@NonNull Call<List<Milestones>> call, @NonNull Throwable t) {
Toasty.error(ctx, getString(R.string.genericServerResponseError));
}
});
}
private void setDueDate() {
final Calendar c = Calendar.getInstance();
int mYear = c.get(Calendar.YEAR);
final int mMonth = c.get(Calendar.MONTH);
final int mDay = c.get(Calendar.DAY_OF_MONTH);
DatePickerDialog datePickerDialog = new DatePickerDialog(this,
(view, year, monthOfYear, dayOfMonth) -> viewBinding.prDueDate.setText(getString(R.string.setDueDate, year, (monthOfYear + 1), dayOfMonth)), mYear, mMonth, mDay);
datePickerDialog.show();
}
private void initCloseListener() {
onClickListener = view -> finish();
}
private void disableProcessButton() {
viewBinding.createPr.setEnabled(false);
}
private void enableProcessButton() {
viewBinding.createPr.setEnabled(true);
}
}

View File

@ -1,11 +1,6 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import retrofit2.Call;
import retrofit2.Callback;
import android.content.Context;
import android.graphics.PorterDuff;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
@ -17,17 +12,20 @@ import android.widget.CheckBox;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.Spinner;
import androidx.annotation.NonNull;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.Branches;
import org.mian.gitnex.models.Releases;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
@ -60,7 +58,7 @@ public class CreateReleaseActivity extends BaseActivity {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
@ -88,7 +86,6 @@ public class CreateReleaseActivity extends BaseActivity {
closeActivity.setOnClickListener(onClickListener);
releaseBranch = findViewById(R.id.releaseBranch);
releaseBranch.getBackground().setColorFilter(getResources().getColor(R.color.white), PorterDuff.Mode.SRC_ATOP);
getBranches(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName);
releaseBranch.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
@Override
@ -108,24 +105,19 @@ public class CreateReleaseActivity extends BaseActivity {
if(!connToInternet) {
disableProcessButton();
} else {
}
else {
createNewRelease.setOnClickListener(createReleaseListener);
}
}
private View.OnClickListener createReleaseListener = new View.OnClickListener() {
public void onClick(View v) {
processNewRelease();
}
};
private View.OnClickListener createReleaseListener = v -> processNewRelease();
private void processNewRelease() {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
@ -145,21 +137,21 @@ public class CreateReleaseActivity extends BaseActivity {
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if(newReleaseTagName.equals("")) {
Toasty.info(ctx, getString(R.string.tagNameErrorEmpty));
Toasty.error(ctx, getString(R.string.tagNameErrorEmpty));
return;
}
if(newReleaseTitle.equals("")) {
Toasty.info(ctx, getString(R.string.titleErrorEmpty));
Toasty.error(ctx, getString(R.string.titleErrorEmpty));
return;
}
@ -189,7 +181,7 @@ public class CreateReleaseActivity extends BaseActivity {
TinyDB tinyDb = new TinyDB(appCtx);
tinyDb.putBoolean("updateReleases", true);
Toasty.info(ctx, getString(R.string.releaseCreatedText));
Toasty.success(ctx, getString(R.string.releaseCreatedText));
enableProcessButton();
finish();
@ -206,19 +198,19 @@ public class CreateReleaseActivity extends BaseActivity {
else if(response.code() == 403) {
enableProcessButton();
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
enableProcessButton();
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else {
enableProcessButton();
Toasty.info(ctx, ctx.getString(R.string.genericError));
Toasty.error(ctx, ctx.getString(R.string.genericError));
}
@ -302,21 +294,11 @@ public class CreateReleaseActivity extends BaseActivity {
private void disableProcessButton() {
createNewRelease.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createNewRelease.setBackground(shape);
}
private void enableProcessButton() {
createNewRelease.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
createNewRelease.setBackground(shape);
}
}

View File

@ -1,10 +1,7 @@
package org.mian.gitnex.activities;
import android.content.Context;
import android.graphics.PorterDuff;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import androidx.annotation.NonNull;
import android.util.Log;
import android.view.View;
import android.view.inputmethod.InputMethodManager;
@ -15,15 +12,16 @@ import android.widget.CheckBox;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.Spinner;
import androidx.annotation.NonNull;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.OrgOwner;
import org.mian.gitnex.models.OrganizationRepository;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
@ -64,7 +62,7 @@ public class CreateRepoActivity extends BaseActivity {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
boolean connToInternet = AppUtil.haveNetworkConnection(ctx);
boolean connToInternet = AppUtil.hasNetworkConnection(ctx);
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
@ -87,8 +85,8 @@ public class CreateRepoActivity extends BaseActivity {
closeActivity.setOnClickListener(onClickListener);
spinner = findViewById(R.id.ownerSpinner);
spinner.getBackground().setColorFilter(getResources().getColor(R.color.white), PorterDuff.Mode.SRC_ATOP);
getOrganizations(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), userLogin);
spinner.setOnItemSelectedListener(new AdapterView.OnItemSelectedListener() {
@Override
public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
@ -107,12 +105,10 @@ public class CreateRepoActivity extends BaseActivity {
if(!connToInternet) {
disableProcessButton();
}
else {
createRepo.setOnClickListener(createRepoListener);
}
}
@ -124,7 +120,7 @@ public class CreateRepoActivity extends BaseActivity {
private void processNewRepo() {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
AppUtil appUtil = new AppUtil();
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
@ -138,45 +134,38 @@ public class CreateRepoActivity extends BaseActivity {
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if(!newRepoDesc.equals("")) {
if (appUtil.charactersLength(newRepoDesc) > 255) {
Toasty.info(ctx, getString(R.string.repoDescError));
Toasty.warning(ctx, getString(R.string.repoDescError));
return;
}
}
if(newRepoName.equals("")) {
Toasty.info(ctx, getString(R.string.repoNameErrorEmpty));
Toasty.error(ctx, getString(R.string.repoNameErrorEmpty));
}
else if(!appUtil.checkStrings(newRepoName)) {
Toasty.info(ctx, getString(R.string.repoNameErrorInvalid));
Toasty.warning(ctx, getString(R.string.repoNameErrorInvalid));
}
else if (reservedRepoNames.contains(newRepoName)) {
Toasty.info(ctx, getString(R.string.repoNameErrorReservedName));
Toasty.warning(ctx, getString(R.string.repoNameErrorReservedName));
}
else if (reservedRepoPatterns.matcher(newRepoName).find()) {
Toasty.info(ctx, getString(R.string.repoNameErrorReservedPatterns));
Toasty.warning(ctx, getString(R.string.repoNameErrorReservedPatterns));
}
else {
disableProcessButton();
createNewRepository(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), loginUid, newRepoName, newRepoDesc, repoOwner, newRepoAccess);
}
}
@ -191,7 +180,6 @@ public class CreateRepoActivity extends BaseActivity {
.getInstance(instanceUrl, ctx)
.getApiInterface()
.createNewUserRepository(token, createRepository);
}
else {
@ -199,7 +187,6 @@ public class CreateRepoActivity extends BaseActivity {
.getInstance(instanceUrl, ctx)
.getApiInterface()
.createNewUserOrgRepository(token, repoOwner, createRepository);
}
call.enqueue(new Callback<OrganizationRepository>() {
@ -211,7 +198,7 @@ public class CreateRepoActivity extends BaseActivity {
TinyDB tinyDb = new TinyDB(appCtx);
tinyDb.putBoolean("repoCreated", true);
Toasty.info(ctx, getString(R.string.repoCreated));
Toasty.success(ctx, getString(R.string.repoCreated));
enableProcessButton();
finish();
}
@ -222,25 +209,23 @@ public class CreateRepoActivity extends BaseActivity {
getResources().getString(R.string.alertDialogTokenRevokedMessage),
getResources().getString(R.string.alertDialogTokenRevokedCopyNegativeButton),
getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
}
else if(response.code() == 409) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.repoExistsError));
Toasty.warning(ctx, getString(R.string.repoExistsError));
}
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.repoCreatedError));
Toasty.error(ctx, getString(R.string.repoCreatedError));
}
}
@Override
public void onFailure(@NonNull Call<OrganizationRepository> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
enableProcessButton();
}
@ -271,13 +256,16 @@ public class CreateRepoActivity extends BaseActivity {
organizationsList.add(new OrgOwner(userLogin));
assert organizationsList_ != null;
if(organizationsList_.size() > 0) {
for (int i = 0; i < organizationsList_.size(); i++) {
if(!tinyDb.getString("organizationId").isEmpty()) {
if (Integer.parseInt(tinyDb.getString("organizationId")) == organizationsList_.get(i).getId()) {
organizationId = i + 1;
}
}
OrgOwner data = new OrgOwner(
organizationsList_.get(i).getUsername()
);
@ -293,6 +281,7 @@ public class CreateRepoActivity extends BaseActivity {
spinner.setAdapter(adapter);
if (tinyDb.getBoolean("organizationAction") & organizationId != 0) {
spinner.setSelection(organizationId);
tinyDb.putBoolean("organizationAction", false);
}
@ -308,13 +297,13 @@ public class CreateRepoActivity extends BaseActivity {
getResources().getString(R.string.alertDialogTokenRevokedMessage),
getResources().getString(R.string.alertDialogTokenRevokedCopyNegativeButton),
getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
}
}
@Override
public void onFailure(@NonNull Call<List<OrgOwner>> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
enableProcessButton();
}
@ -322,32 +311,18 @@ public class CreateRepoActivity extends BaseActivity {
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
onClickListener = view -> finish();
}
private void disableProcessButton() {
createRepo.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
createRepo.setBackground(shape);
}
private void enableProcessButton() {
createRepo.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
createRepo.setBackground(shape);
}
}

View File

@ -1,30 +1,29 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AlertDialog;
import retrofit2.Call;
import retrofit2.Callback;
import android.content.Context;
import android.content.DialogInterface;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.view.inputmethod.InputMethodManager;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AlertDialog;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.Teams;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import android.util.Log;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
@ -78,7 +77,7 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
@ -98,9 +97,7 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
teamPermission.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
teamPermission.setOnClickListener(view -> {
AlertDialog.Builder pBuilder = new AlertDialog.Builder(ctx);
@ -111,44 +108,44 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
else {
pBuilder.setCancelable(false);
}
pBuilder.setSingleChoiceItems(permissionList, permissionSelectedChoice, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialogInterface, int i) {
pBuilder.setSingleChoiceItems(permissionList, permissionSelectedChoice, (dialogInterface, i) -> {
permissionSelectedChoice = i;
teamPermission.setText(permissionList[i]);
if(permissionList[i].equals("Read")) {
switch(permissionList[i]) {
case "Read":
teamPermissionDetail.setVisibility(View.VISIBLE);
teamPermissionDetail.setText(R.string.newTeamPermissionRead);
}
else if(permissionList[i].equals("Write")) {
break;
case "Write":
teamPermissionDetail.setVisibility(View.VISIBLE);
teamPermissionDetail.setText(R.string.newTeamPermissionWrite);
}
else if(permissionList[i].equals("Admin")) {
break;
case "Admin":
teamPermissionDetail.setVisibility(View.VISIBLE);
teamPermissionDetail.setText(R.string.newTeamPermissionAdmin);
}
else {
break;
default:
teamPermissionDetail.setVisibility(View.GONE);
break;
}
dialogInterface.dismiss();
}
});
AlertDialog pDialog = pBuilder.create();
pDialog.show();
}
});
teamAccessControls.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
teamAccessControls.setOnClickListener(v -> {
teamAccessControls.setText("");
teamAccessControlsArray.setText("");
@ -156,20 +153,12 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
AlertDialog.Builder aDialogBuilder = new AlertDialog.Builder(ctx);
aDialogBuilder.setMultiChoiceItems(accessControlsList, selectedAccessControlsTrueFalse, new DialogInterface.OnMultiChoiceClickListener() {
@Override
public void onClick(DialogInterface dialog, int which, boolean isChecked) {
}
aDialogBuilder.setMultiChoiceItems(accessControlsList, selectedAccessControlsTrueFalse, (dialog, which, isChecked) -> {
})
.setCancelable(false)
.setTitle(R.string.newTeamAccessControls)
.setPositiveButton(R.string.okButton, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialog, int which) {
.setPositiveButton(R.string.okButton, (dialog, which) -> {
int selectedVal = 0;
while(selectedVal < selectedAccessControlsTrueFalse.length)
@ -218,14 +207,10 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
}
//Log.i("orgName", String.valueOf(teamAccessControlsArray.getText()));
}
});
AlertDialog aDialog = aDialogBuilder.create();
aDialog.show();
}
});
createTeamButton.setEnabled(false);
@ -256,7 +241,7 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
final String orgName = tinyDb.getString("orgName");;
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
String newTeamName = teamName.getText().toString();
String newTeamDesc = teamDesc.getText().toString();
String newTeamPermission = teamPermission.getText().toString().toLowerCase();
@ -264,21 +249,21 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if (newTeamName.equals("")) {
Toasty.info(ctx, getString(R.string.teamNameEmpty));
Toasty.error(ctx, getString(R.string.teamNameEmpty));
return;
}
if(!appUtil.checkStringsWithAlphaNumericDashDotUnderscore(newTeamName)) {
Toasty.info(ctx, getString(R.string.teamNameError));
Toasty.warning(ctx, getString(R.string.teamNameError));
return;
}
@ -286,12 +271,12 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
if(!newTeamDesc.equals("")) {
if(!appUtil.checkStrings(newTeamDesc)) {
Toasty.info(ctx, getString(R.string.teamDescError));
Toasty.warning(ctx, getString(R.string.teamDescError));
return;
}
if(newTeamDesc.length() > 100) {
Toasty.info(ctx, getString(R.string.teamDescLimit));
Toasty.warning(ctx, getString(R.string.teamDescLimit));
return;
}
@ -299,7 +284,7 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
if (newTeamPermission.equals("")) {
Toasty.info(ctx, getString(R.string.teamPermissionEmpty));
Toasty.error(ctx, getString(R.string.teamPermissionEmpty));
return;
}
@ -336,16 +321,14 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
TinyDB tinyDb = new TinyDB(appCtx);
tinyDb.putBoolean("resumeTeams", true);
Toasty.info(ctx, getString(R.string.teamCreated));
Toasty.success(ctx, getString(R.string.teamCreated));
finish();
}
}
else if(response2.code() == 404) {
Toasty.info(ctx, getString(R.string.apiNotFound));
Toasty.warning(ctx, getString(R.string.apiNotFound));
}
else if(response2.code() == 401) {
@ -353,12 +336,10 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
getResources().getString(R.string.alertDialogTokenRevokedMessage),
getResources().getString(R.string.alertDialogTokenRevokedCopyNegativeButton),
getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
}
else {
Toasty.info(ctx, getString(R.string.teamCreatedError));
Toasty.error(ctx, getString(R.string.teamCreatedError));
}
}
@ -373,19 +354,15 @@ public class CreateTeamByOrgActivity extends BaseActivity implements View.OnClic
@Override
public void onClick(View v) {
if(v == createTeamButton) {
processCreateTeam();
}
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
onClickListener = view -> finish();
}
}

View File

@ -1,68 +0,0 @@
package org.mian.gitnex.activities;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import android.content.Context;
import android.content.res.Resources;
import android.os.Bundle;
import android.view.View;
import android.widget.ImageView;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.CreditsAdapter;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
/**
* Author M M Arif
*/
public class CreditsActivity extends BaseActivity {
private View.OnClickListener onClickListener;
final Context ctx = this;
@Override
protected int getLayoutResourceId(){
return R.layout.activity_credits;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
ImageView closeActivity = findViewById(R.id.close);
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
Resources res = getResources();
CharSequence[] creditsInfo = res.getTextArray(R.array.creditsInfo);
List<CharSequence> creditsList = new ArrayList<>(Arrays.asList(creditsInfo));
RecyclerView mRecyclerView = findViewById(R.id.recyclerView);
mRecyclerView.setHasFixedSize(true);
mRecyclerView.setLayoutManager(new LinearLayoutManager(ctx));
DividerItemDecoration dividerItemDecoration = new DividerItemDecoration(mRecyclerView.getContext(),
DividerItemDecoration.VERTICAL);
mRecyclerView.addItemDecoration(dividerItemDecoration);
CreditsAdapter adapter = new CreditsAdapter(creditsList);
mRecyclerView.setAdapter(adapter);
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
}
}

View File

@ -1,14 +1,8 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import android.annotation.SuppressLint;
import android.app.DatePickerDialog;
import android.content.Context;
import android.graphics.PorterDuff;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
@ -20,6 +14,7 @@ import android.widget.EditText;
import android.widget.ImageView;
import android.widget.Spinner;
import android.widget.TextView;
import androidx.annotation.NonNull;
import com.google.gson.JsonElement;
import com.hendraanggrian.appcompat.socialview.Mention;
import com.hendraanggrian.appcompat.widget.MentionArrayAdapter;
@ -27,21 +22,24 @@ import com.hendraanggrian.appcompat.widget.SocialAutoCompleteTextView;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.StaticGlobalVariables;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.Collaborators;
import org.mian.gitnex.models.CreateIssue;
import org.mian.gitnex.models.Issues;
import org.mian.gitnex.models.Milestones;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
/**
* Author M M Arif
@ -109,7 +107,6 @@ public class EditIssueActivity extends BaseActivity implements View.OnClickListe
loadCollaboratorsList();
editIssueMilestoneSpinner = findViewById(R.id.editIssueMilestoneSpinner);
editIssueMilestoneSpinner.getBackground().setColorFilter(getResources().getColor(R.color.white), PorterDuff.Mode.SRC_ATOP);
editIssueDescription.setMentionAdapter(defaultMentionAdapter);
@ -121,7 +118,7 @@ public class EditIssueActivity extends BaseActivity implements View.OnClickListe
if(!tinyDb.getString("issueNumber").isEmpty()) {
if(tinyDb.getString("issueType").equals("pr")) {
if(tinyDb.getString("issueType").equalsIgnoreCase("Pull")) {
toolbar_title.setText(getString(R.string.editPrNavHeader, String.valueOf(issueIndex)));
}
else {
@ -196,7 +193,7 @@ public class EditIssueActivity extends BaseActivity implements View.OnClickListe
private void processEditIssue() {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
final String loginUid = tinyDb.getString("loginUid");
@ -217,14 +214,14 @@ public class EditIssueActivity extends BaseActivity implements View.OnClickListe
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if (editIssueTitleForm.equals("")) {
Toasty.info(ctx, getString(R.string.issueTitleEmpty));
Toasty.error(ctx, getString(R.string.issueTitleEmpty));
return;
}
@ -266,11 +263,11 @@ public class EditIssueActivity extends BaseActivity implements View.OnClickListe
if(response.code() == 201) {
if(tinyDb.getString("issueType").equals("pr")) {
Toasty.info(ctx, getString(R.string.editPrSuccessMessage));
if(tinyDb.getString("issueType").equalsIgnoreCase("Pull")) {
Toasty.success(ctx, getString(R.string.editPrSuccessMessage));
}
else {
Toasty.info(ctx, getString(R.string.editIssueSuccessMessage));
Toasty.success(ctx, getString(R.string.editIssueSuccessMessage));
}
tinyDb.putBoolean("issueEdited", true);
@ -290,7 +287,7 @@ public class EditIssueActivity extends BaseActivity implements View.OnClickListe
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.genericError));
Toasty.error(ctx, getString(R.string.genericError));
}
@ -427,7 +424,6 @@ public class EditIssueActivity extends BaseActivity implements View.OnClickListe
@SuppressLint("SimpleDateFormat") DateFormat formatter = new SimpleDateFormat("yyyy-M-dd");
String dueDate = formatter.format(response.body().getDue_date());
editIssueDueDate.setText(dueDate);
}
//enableProcessButton();
@ -438,12 +434,10 @@ public class EditIssueActivity extends BaseActivity implements View.OnClickListe
getResources().getString(R.string.alertDialogTokenRevokedMessage),
getResources().getString(R.string.alertDialogTokenRevokedCopyNegativeButton),
getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
}
else {
Toasty.info(ctx, getString(R.string.genericError));
Toasty.error(ctx, getString(R.string.genericError));
}
}
@ -459,21 +453,11 @@ public class EditIssueActivity extends BaseActivity implements View.OnClickListe
private void disableProcessButton() {
editIssueButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
editIssueButton.setBackground(shape);
}
private void enableProcessButton() {
editIssueButton.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
editIssueButton.setBackground(shape);
}
}

View File

@ -10,17 +10,17 @@ import android.widget.ProgressBar;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.widget.Toolbar;
import org.apache.commons.io.FileUtils;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.FilesDiffAdapter;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.ParseDiff;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.FileDiffView;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import okhttp3.ResponseBody;
import retrofit2.Call;
@ -33,7 +33,7 @@ import retrofit2.Callback;
public class FileDiffActivity extends BaseActivity {
private View.OnClickListener onClickListener;
private TextView toolbar_title;
private TextView toolbarTitle;
private ListView mListView;
private ProgressBar mProgressBar;
final Context ctx = this;
@ -41,6 +41,7 @@ public class FileDiffActivity extends BaseActivity {
@Override
protected int getLayoutResourceId() {
return R.layout.activity_file_diff;
}
@ -58,18 +59,17 @@ public class FileDiffActivity extends BaseActivity {
String[] parts = repoFullName.split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
final String instanceUrl = tinyDb.getString("instanceUrl");
final String loginUid = tinyDb.getString("loginUid");
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
ImageView closeActivity = findViewById(R.id.close);
toolbar_title = findViewById(R.id.toolbar_title);
toolbarTitle = findViewById(R.id.toolbar_title);
mListView = findViewById(R.id.listView);
mProgressBar = findViewById(R.id.progress_bar);
mListView.setDivider(null);
toolbar_title.setText(R.string.processingText);
toolbarTitle.setText(R.string.processingText);
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
@ -77,16 +77,29 @@ public class FileDiffActivity extends BaseActivity {
String pullIndex = tinyDb.getString("issueNumber");
getPullDiffContent(tinyDb.getString("instanceUrlWithProtocol"), repoOwner, repoName, pullIndex);
boolean apiCall = true;
String instanceUrl = tinyDb.getString("instanceUrl");
// fallback for old gitea instances
if(new Version(tinyDb.getString("giteaVersion")).less("1.13.0")) {
apiCall = false;
instanceUrl = instanceUrl.substring(0, instanceUrl.lastIndexOf("api/v1/"));
}
getPullDiffContent(instanceUrl, repoOwner, repoName, pullIndex, instanceToken, apiCall);
}
private void getPullDiffContent(String instanceUrl, String owner, String repo, String filename) {
private void getPullDiffContent(String instanceUrl, String owner, String repo, String pullIndex, String token, boolean apiCall) {
Call<ResponseBody> call = RetrofitClient
.getInstance(instanceUrl, ctx)
.getWebInterface()
.getPullDiffContent(owner, repo, filename);
Call<ResponseBody> call;
if(apiCall) {
call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().getPullDiffContent(token, owner, repo, pullIndex);
}
else {
call = RetrofitClient.getInstance(instanceUrl, ctx).getWebInterface().getPullDiffContent(owner, repo, pullIndex);
}
call.enqueue(new Callback<ResponseBody>() {
@ -99,69 +112,14 @@ public class FileDiffActivity extends BaseActivity {
assert response.body() != null;
AppUtil appUtil = new AppUtil();
List<FileDiffView> fileContentsArray = new ArrayList<>();
String[] lines = response.body().string().split("diff");
if(lines.length > 0) {
for (int i = 1; i < lines.length; i++) {
if(lines[i].contains("@@ -")) {
String[] level2nd = lines[i].split("@@ -"); // main content part of single diff view
String[] fileName_ = level2nd[0].split("\\+\\+\\+ b/"); // filename part
String fileNameFinal = fileName_[1];
String[] fileContents_ = level2nd[1].split("@@"); // file info / content part
String fileInfoFinal = fileContents_[0];
StringBuilder fileContentsFinal = new StringBuilder(fileContents_[1]);
if(level2nd.length > 2) {
for (int j = 2; j < level2nd.length; j++) {
fileContentsFinal.append(level2nd[j]);
}
}
String fileExtension = FileUtils.getExtension(fileNameFinal);
String fileContentsFinalWithBlankLines = fileContentsFinal.toString().replaceAll( ".*@@.*", "" );
String fileContentsFinalWithoutBlankLines = fileContentsFinal.toString().replaceAll( ".*@@.*(\r?\n|\r)?", "" );
fileContentsFinalWithoutBlankLines = fileContentsFinalWithoutBlankLines.replaceAll( ".*\\ No newline at end of file.*(\r?\n|\r)?", "" );
fileContentsArray.add(new FileDiffView(fileNameFinal, appUtil.imageExtension(fileExtension), fileInfoFinal, fileContentsFinalWithoutBlankLines));
}
else {
String[] getFileName = lines[i].split("--git a/");
String[] getFileName_ = getFileName[1].split("b/");
String getFileNameFinal = getFileName_[0].trim();
String[] binaryFile = getFileName_[1].split("GIT binary patch");
String binaryFileRaw = binaryFile[1].substring(binaryFile[1].indexOf('\n')+1);
String binaryFileFinal = binaryFile[1].substring(binaryFileRaw.indexOf('\n')+1);
String fileExtension = FileUtils.getExtension(getFileNameFinal);
if(appUtil.imageExtension(FileUtils.getExtension(getFileNameFinal))) {
fileContentsArray.add(new FileDiffView(getFileNameFinal, appUtil.imageExtension(fileExtension), "", binaryFileFinal));
}
}
}
}
List<FileDiffView> fileContentsArray = ParseDiff.getFileDiffViewArray(response.body().string());
int filesCount = fileContentsArray.size();
if(filesCount > 1) {
toolbar_title.setText(getResources().getString(R.string.fileDiffViewHeader, Integer.toString(filesCount)));
toolbarTitle.setText(getResources().getString(R.string.fileDiffViewHeader, Integer.toString(filesCount)));
}
else {
toolbar_title.setText(getResources().getString(R.string.fileDiffViewHeaderSingle, Integer.toString(filesCount)));
toolbarTitle.setText(getResources().getString(R.string.fileDiffViewHeaderSingle, Integer.toString(filesCount)));
}
FilesDiffAdapter adapter = new FilesDiffAdapter(ctx, fileContentsArray);
@ -169,32 +127,30 @@ public class FileDiffActivity extends BaseActivity {
mProgressBar.setVisibility(View.GONE);
} catch (IOException e) {
}
catch(IOException e) {
e.printStackTrace();
}
}
else if(response.code() == 401) {
AlertDialogs.authorizationTokenRevokedDialog(ctx, getResources().getString(R.string.alertDialogTokenRevokedTitle),
getResources().getString(R.string.alertDialogTokenRevokedMessage),
getResources().getString(R.string.alertDialogTokenRevokedCopyNegativeButton),
getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
AlertDialogs.authorizationTokenRevokedDialog(ctx, getResources().getString(R.string.alertDialogTokenRevokedTitle), getResources().getString(R.string.alertDialogTokenRevokedMessage), getResources().getString(R.string.alertDialogTokenRevokedCopyNegativeButton), getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
}
else if(response.code() == 403) {
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else {
Toasty.info(ctx, getString(R.string.labelGeneralError));
Toasty.error(ctx, getString(R.string.labelGeneralError));
}
@ -202,6 +158,7 @@ public class FileDiffActivity extends BaseActivity {
@Override
public void onFailure(@NonNull Call<ResponseBody> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
}
});
@ -209,12 +166,11 @@ public class FileDiffActivity extends BaseActivity {
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
onClickListener = view -> {
getIntent().removeExtra("singleFileName");
finish();
}
};
}

View File

@ -8,6 +8,7 @@ import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
import android.net.Uri;
import android.os.Bundle;
import android.text.Spanned;
import android.text.method.ScrollingMovementMethod;
import android.util.Base64;
import android.util.Log;
@ -31,18 +32,35 @@ import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.fragments.BottomSheetFileViewerFragment;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.highlightjs.HighlightJsView;
import org.mian.gitnex.helpers.highlightjs.models.Theme;
import org.mian.gitnex.models.Files;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.io.File;
import java.io.IOException;
import java.io.OutputStream;
import java.io.UnsupportedEncodingException;
import java.net.URLDecoder;
import java.util.Collection;
import java.util.Collections;
import java.util.Objects;
import io.noties.markwon.AbstractMarkwonPlugin;
import io.noties.markwon.Markwon;
import io.noties.markwon.core.CorePlugin;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.ext.tables.TablePlugin;
import io.noties.markwon.ext.tasklist.TaskListPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.image.DefaultMediaDecoder;
import io.noties.markwon.image.ImageItem;
import io.noties.markwon.image.ImagesPlugin;
import io.noties.markwon.image.SchemeHandler;
import io.noties.markwon.image.gif.GifMediaDecoder;
import io.noties.markwon.image.svg.SvgMediaDecoder;
import io.noties.markwon.linkify.LinkifyPlugin;
import retrofit2.Call;
import retrofit2.Callback;
@ -65,6 +83,10 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
private LinearLayout pdfViewFrame;
private byte[] decodedPdf;
private Boolean pdfNightMode;
private String singleFileName;
private String fileSha;
private AppUtil appUtil;
private TinyDB tinyDb;
@Override
protected int getLayoutResourceId() {
@ -77,12 +99,14 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
appUtil = new AppUtil();
tinyDb = new TinyDB(appCtx);
Toolbar toolbar = findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
final TinyDB tinyDb = new TinyDB(appCtx);
String repoFullName = tinyDb.getString("repoFullName");
String repoBranch = tinyDb.getString("repoBranch");
String[] parts = repoFullName.split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
@ -90,6 +114,8 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
final String loginUid = tinyDb.getString("loginUid");
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
tinyDb.putBoolean("enableMarkdownInFileView", false);
ImageView closeActivity = findViewById(R.id.close);
singleFileContents = findViewById(R.id.singleFileContents);
singleCodeContents = findViewById(R.id.singleCodeContents);
@ -99,7 +125,7 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
pdfViewFrame = findViewById(R.id.pdfViewFrame);
singleFileContentsFrame = findViewById(R.id.singleFileContentsFrame);
String singleFileName = getIntent().getStringExtra("singleFileName");
singleFileName = getIntent().getStringExtra("singleFileName");
TextView toolbar_title = findViewById(R.id.toolbar_title);
toolbar_title.setMovementMethod(new ScrollingMovementMethod());
@ -118,22 +144,40 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
}
catch(UnsupportedEncodingException e) {
assert singleFileName != null;
Log.i("singleFileName", singleFileName);
}
toolbar_title.setText(singleFileName);
getSingleFileContents(instanceUrl, instanceToken, repoOwner, repoName, singleFileName);
getSingleFileContents(instanceUrl, instanceToken, repoOwner, repoName, singleFileName, repoBranch);
}
private void getSingleFileContents(String instanceUrl, String token, final String owner, String repo, final String filename) {
@Override
public void onResume() {
final TinyDB tinyDb = new TinyDB(appCtx);
super.onResume();
Call<Files> call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().getSingleFileContents(token, owner, repo, filename);
String repoFullName = tinyDb.getString("repoFullName");
String repoBranch = tinyDb.getString("repoBranch");
String[] parts = repoFullName.split("/");
String repoOwner = parts[0];
String repoName = parts[1];
String instanceUrl = tinyDb.getString("instanceUrl");
String loginUid = tinyDb.getString("loginUid");
String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
if(tinyDb.getBoolean("fileModified")) {
getSingleFileContents(instanceUrl, instanceToken, repoOwner, repoName, singleFileName, repoBranch);
tinyDb.putBoolean("fileModified", false);
}
}
private void getSingleFileContents(String instanceUrl, String token, final String owner, String repo, final String filename, String ref) {
Call<Files> call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().getSingleFileContents(token, owner, repo, filename, ref);
call.enqueue(new Callback<Files>() {
@ -142,7 +186,6 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
if(response.code() == 200) {
AppUtil appUtil = new AppUtil();
assert response.body() != null;
if(!response.body().getContent().equals("")) {
@ -150,6 +193,8 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
String fileExtension = FileUtils.getExtension(filename);
mProgressBar.setVisibility(View.GONE);
fileSha = response.body().getSha();
// download file meta
tinyDb.putString("downloadFileName", filename);
tinyDb.putString("downloadFileContents", response.body().getContent());
@ -246,17 +291,17 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
}
else if(response.code() == 403) {
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else {
Toasty.info(ctx, getString(R.string.labelGeneralError));
Toasty.error(ctx, getString(R.string.labelGeneralError));
}
@ -276,6 +321,13 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.generic_nav_dotted_menu, menu);
inflater.inflate(R.menu.files_view_menu, menu);
String fileExtension = FileUtils.getExtension(singleFileName);
if(!fileExtension.equalsIgnoreCase("md")) {
menu.getItem(0).setVisible(false);
}
return true;
}
@ -286,11 +338,82 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
switch(id) {
case android.R.id.home:
finish();
return true;
case R.id.genericMenu:
BottomSheetFileViewerFragment bottomSheet = new BottomSheetFileViewerFragment();
bottomSheet.show(getSupportFragmentManager(), "fileViewerBottomSheet");
return true;
case R.id.markdown:
final Markwon markwon = Markwon.builder(Objects.requireNonNull(ctx)).usePlugin(CorePlugin.create())
.usePlugin(ImagesPlugin.create(plugin -> {
plugin.addSchemeHandler(new SchemeHandler() {
@NonNull
@Override
public ImageItem handle(@NonNull String raw, @NonNull Uri uri) {
final int resourceId = ctx.getResources().getIdentifier(
raw.substring("drawable://".length()),
"drawable",
ctx.getPackageName());
final Drawable drawable = ctx.getDrawable(resourceId);
assert drawable != null;
return ImageItem.withResult(drawable);
}
@NonNull
@Override
public Collection<String> supportedSchemes() {
return Collections.singleton("drawable");
}
});
plugin.placeholderProvider(drawable -> null);
plugin.addMediaDecoder(GifMediaDecoder.create(false));
plugin.addMediaDecoder(SvgMediaDecoder.create(ctx.getResources()));
plugin.addMediaDecoder(SvgMediaDecoder.create());
plugin.defaultMediaDecoder(DefaultMediaDecoder.create(ctx.getResources()));
plugin.defaultMediaDecoder(DefaultMediaDecoder.create());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@Override
public void configureTheme(@NonNull MarkwonTheme.Builder builder) {
builder.codeTextColor(tinyDb.getInt("codeBlockColor")).codeBackgroundColor(tinyDb.getInt("codeBlockBackground"))
.linkColor(getResources().getColor(R.color.lightBlue));
}
})
.usePlugin(TablePlugin.create(ctx))
.usePlugin(TaskListPlugin.create(ctx))
.usePlugin(HtmlPlugin.create())
.usePlugin(StrikethroughPlugin.create())
.usePlugin(LinkifyPlugin.create())
.build();
if(!tinyDb.getBoolean("enableMarkdownInFileView")) {
singleCodeContents.setVisibility(View.GONE);
singleFileContentsFrame.setVisibility(View.VISIBLE);
singleFileContents.setVisibility(View.VISIBLE);
Spanned bodyWithMD = markwon.toMarkdown(appUtil.decodeBase64(tinyDb.getString("downloadFileContents")));
markwon.setParsedMarkdown(singleFileContents, bodyWithMD);
tinyDb.putBoolean("enableMarkdownInFileView", true);
}
else {
singleCodeContents.setVisibility(View.VISIBLE);
singleFileContentsFrame.setVisibility(View.GONE);
singleFileContents.setVisibility(View.GONE);
singleCodeContents.setSource(appUtil.decodeBase64(tinyDb.getString("downloadFileContents")));
tinyDb.putBoolean("enableMarkdownInFileView", false);
}
return true;
default:
return super.onOptionsItemSelected(item);
@ -304,15 +427,48 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
if("downloadFile".equals(text)) {
requestFileDownload();
}
if("deleteFile".equals(text)) {
String fileExtension = FileUtils.getExtension(singleFileName);
String data = appUtil.decodeBase64(tinyDb.getString("downloadFileContents"));
Intent intent = new Intent(ctx, CreateFileActivity.class);
intent.putExtra("fileAction", 1);
intent.putExtra("filePath", singleFileName);
intent.putExtra("fileSha", fileSha);
if(!appUtil.imageExtension(fileExtension)) {
intent.putExtra("fileContents", data);
}
else {
intent.putExtra("fileContents", "");
}
ctx.startActivity(intent);
}
if("editFile".equals(text)) {
String fileExtension = FileUtils.getExtension(singleFileName);
String data = appUtil.decodeBase64(tinyDb.getString("downloadFileContents"));
Intent intent = new Intent(ctx, CreateFileActivity.class);
intent.putExtra("fileAction", 2);
intent.putExtra("filePath", singleFileName);
intent.putExtra("fileSha", fileSha);
if(!appUtil.imageExtension(fileExtension)) {
intent.putExtra("fileContents", data);
}
else {
intent.putExtra("fileContents", "");
}
ctx.startActivity(intent);
}
}
private void requestFileDownload() {
final TinyDB tinyDb = new TinyDB(appCtx);
if(!tinyDb.getString("downloadFileContents").isEmpty()) {
int CREATE_REQUEST_CODE = 40;
@ -329,7 +485,8 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
}
else {
Toasty.error(ctx, getString(R.string.waitLoadingDownloadFile));
Toasty.warning(ctx, getString(R.string.waitLoadingDownloadFile));
}
}
@ -339,8 +496,6 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
super.onActivityResult(requestCode, resultCode, data);
final TinyDB tinyDb = new TinyDB(appCtx);
if(requestCode == 40 && resultCode == RESULT_OK) {
try {
@ -357,10 +512,11 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
outputStream.write(dataAsBytes);
outputStream.close();
Toasty.info(ctx, getString(R.string.downloadFileSaved));
Toasty.success(ctx, getString(R.string.downloadFileSaved));
}
catch(IOException e) {
Log.e("errorFileDownloading", Objects.requireNonNull(e.getMessage()));
}
@ -374,7 +530,6 @@ public class FileViewActivity extends BaseActivity implements BottomSheetFileVie
getIntent().removeExtra("singleFileName");
finish();
};
}

View File

@ -25,15 +25,14 @@ import android.widget.RelativeLayout;
import android.widget.ScrollView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.appcompat.widget.Toolbar;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout;
import com.amulyakhare.textdrawable.TextDrawable;
import com.google.android.material.floatingactionbutton.ExtendedFloatingActionButton;
import com.vdurmont.emoji.EmojiParser;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.IssueCommentsAdapter;
@ -41,24 +40,23 @@ import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.fragments.BottomSheetSingleIssueFragment;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.ClickListener;
import org.mian.gitnex.helpers.ColorInverter;
import org.mian.gitnex.helpers.LabelWidthCalculator;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TimeHelper;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.UserMentions;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.IssueComments;
import org.mian.gitnex.models.Issues;
import org.mian.gitnex.models.WatchInfo;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.viewmodels.IssueCommentsViewModel;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Locale;
import java.util.Objects;
import io.noties.markwon.AbstractMarkwonPlugin;
@ -99,13 +97,14 @@ public class IssueDetailActivity extends BaseActivity {
private HorizontalScrollView assigneesScrollView;
private ScrollView scrollViewComments;
private TextView issueModified;
private ImageView createNewComment;
private ExtendedFloatingActionButton createNewComment;
final Context ctx = this;
private Context appCtx;
private LinearLayout labelsLayout;
private LinearLayout assigneesLayout;
private View divider;
private ProgressBar progressBar;
private ImageView issuePrState;
@Override
protected int getLayoutResourceId() {
@ -147,6 +146,7 @@ public class IssueDetailActivity extends BaseActivity {
assigneesLayout = findViewById(R.id.frameAssignees);
divider = findViewById(R.id.divider);
progressBar = findViewById(R.id.progressBar);
issuePrState = findViewById(R.id.issuePrState);
Toolbar toolbar = findViewById(R.id.toolbar);
TextView toolbarTitle = toolbar.findViewById(R.id.toolbar_title);
@ -191,7 +191,9 @@ public class IssueDetailActivity extends BaseActivity {
swipeRefresh.setOnRefreshListener(() -> new Handler().postDelayed(() -> {
swipeRefresh.setRefreshing(false);
IssueCommentsViewModel.loadIssueComments(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, issueIndex, ctx);
IssueCommentsViewModel
.loadIssueComments(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, issueIndex,
ctx);
}, 500));
@ -265,7 +267,9 @@ public class IssueDetailActivity extends BaseActivity {
if(tinyDb.getBoolean("commentPosted")) {
scrollViewComments.post(() -> {
IssueCommentsViewModel.loadIssueComments(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, issueIndex, ctx);
IssueCommentsViewModel
.loadIssueComments(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, issueIndex,
ctx);
new Handler().postDelayed(() -> scrollViewComments.fullScroll(ScrollView.FOCUS_DOWN), 1000);
@ -277,7 +281,9 @@ public class IssueDetailActivity extends BaseActivity {
if(tinyDb.getBoolean("commentEdited")) {
scrollViewComments.post(() -> {
IssueCommentsViewModel.loadIssueComments(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, issueIndex, ctx);
IssueCommentsViewModel
.loadIssueComments(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, issueIndex,
ctx);
tinyDb.putBoolean("commentEdited", false);
});
@ -315,12 +321,11 @@ public class IssueDetailActivity extends BaseActivity {
IssueCommentsViewModel issueCommentsModel = new ViewModelProvider(this).get(IssueCommentsViewModel.class);
issueCommentsModel.getIssueCommentList(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), owner, repo, index, ctx).observe(this, new Observer<List<IssueComments>>() {
@Override
public void onChanged(@Nullable List<IssueComments> issueCommentsMain) {
issueCommentsModel.getIssueCommentList(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), owner, repo, index, ctx)
.observe(this, issueCommentsMain -> {
assert issueCommentsMain != null;
if(issueCommentsMain.size() > 0) {
divider.setVisibility(View.VISIBLE);
}
@ -328,7 +333,6 @@ public class IssueDetailActivity extends BaseActivity {
adapter = new IssueCommentsAdapter(ctx, issueCommentsMain);
mRecyclerView.setAdapter(adapter);
}
});
}
@ -336,7 +340,8 @@ public class IssueDetailActivity extends BaseActivity {
private void getSingleIssue(String instanceUrl, String instanceToken, String repoOwner, String repoName, int issueIndex, String loginUid) {
final TinyDB tinyDb = new TinyDB(appCtx);
Call<Issues> call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().getIssueByIndex(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, issueIndex);
Call<Issues> call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface()
.getIssueByIndex(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, issueIndex);
call.enqueue(new Callback<Issues>() {
@ -348,14 +353,37 @@ public class IssueDetailActivity extends BaseActivity {
Issues singleIssue = response.body();
assert singleIssue != null;
final Markwon markwon = Markwon.builder(Objects.requireNonNull(ctx)).usePlugin(CorePlugin.create()).usePlugin(ImagesPlugin.create(plugin -> {
issuePrState.setVisibility(View.VISIBLE);
if(singleIssue.getPull_request() != null) {
if(singleIssue.getPull_request().isMerged()) { // merged
issuePrState.setImageResource(R.drawable.ic_pull_request_merged);
}
else if(!singleIssue.getPull_request().isMerged() && singleIssue.getState().equals("closed")) { // closed
issuePrState.setImageResource(R.drawable.ic_pull_request_closed);
}
else { // open
issuePrState.setImageResource(R.drawable.ic_pull_request);
}
}
else if(singleIssue.getState().equals("closed")) { // issue closed
issuePrState.setImageResource(R.drawable.ic_issue_closed_red);
}
final Markwon markwon = Markwon.builder(Objects.requireNonNull(ctx)).usePlugin(CorePlugin.create())
.usePlugin(ImagesPlugin.create(plugin -> {
plugin.addSchemeHandler(new SchemeHandler() {
@NonNull
@Override
public ImageItem handle(@NonNull String raw, @NonNull Uri uri) {
final int resourceId = ctx.getResources().getIdentifier(raw.substring("drawable://".length()), "drawable", ctx.getPackageName());
final int resourceId = ctx.getResources()
.getIdentifier(raw.substring("drawable://".length()), "drawable", ctx.getPackageName());
final Drawable drawable = ctx.getDrawable(resourceId);
@ -382,18 +410,23 @@ public class IssueDetailActivity extends BaseActivity {
@Override
public void configureTheme(@NonNull MarkwonTheme.Builder builder) {
builder.codeTextColor(tinyDb.getInt("codeBlockColor")).codeBackgroundColor(tinyDb.getInt("codeBlockBackground")).linkColor(getResources().getColor(R.color.lightBlue));
builder.codeTextColor(tinyDb.getInt("codeBlockColor")).codeBackgroundColor(tinyDb.getInt("codeBlockBackground"))
.linkColor(getResources().getColor(R.color.lightBlue));
}
}).usePlugin(TablePlugin.create(ctx)).usePlugin(TaskListPlugin.create(ctx)).usePlugin(HtmlPlugin.create()).usePlugin(StrikethroughPlugin.create()).usePlugin(LinkifyPlugin.create()).build();
}).usePlugin(TablePlugin.create(ctx)).usePlugin(TaskListPlugin.create(ctx)).usePlugin(HtmlPlugin.create())
.usePlugin(StrikethroughPlugin.create()).usePlugin(LinkifyPlugin.create()).build();
TinyDB tinyDb = new TinyDB(appCtx);
final String locale = tinyDb.getString("locale");
final String timeFormat = tinyDb.getString("dateFormat");
tinyDb.putString("issueState", singleIssue.getState());
tinyDb.putString("issueTitle", singleIssue.getTitle());
tinyDb.putString("singleIssueHtmlUrl", singleIssue.getHtml_url());
PicassoService.getInstance(ctx).get().load(singleIssue.getUser().getAvatar_url()).placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(120, 120).centerCrop().into(assigneeAvatar);
String issueNumber_ = "<font color='" + appCtx.getResources().getColor(R.color.lightGray) + "'>" + appCtx.getResources().getString(R.string.hash) + singleIssue.getNumber() + "</font>";
PicassoService.getInstance(ctx).get().load(singleIssue.getUser().getAvatar_url()).placeholder(R.drawable.loader_animated)
.transform(new RoundedTransformation(8, 0)).resize(120, 120).centerCrop().into(assigneeAvatar);
String issueNumber_ = "<font color='" + appCtx.getResources().getColor(R.color.lightGray) + "'>" + appCtx.getResources()
.getString(R.string.hash) + singleIssue.getNumber() + "</font>";
issueTitle.setText(Html.fromHtml(issueNumber_ + " " + singleIssue.getTitle()));
String cleanIssueDescription = singleIssue.getBody().trim();
Spanned bodyWithMD = markwon.toMarkdown(EmojiParser.parseToUnicode(cleanIssueDescription));
@ -410,15 +443,19 @@ public class IssueDetailActivity extends BaseActivity {
ImageView assigneesView = new ImageView(ctx);
PicassoService.getInstance(ctx).get().load(singleIssue.getAssignees().get(i).getAvatar_url()).placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(100, 100).centerCrop().into(assigneesView);
PicassoService.getInstance(ctx).get().load(singleIssue.getAssignees().get(i).getAvatar_url())
.placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(100, 100).centerCrop()
.into(assigneesView);
assigneesLayout.addView(assigneesView);
assigneesView.setLayoutParams(params1);
if(!singleIssue.getAssignees().get(i).getFull_name().equals("")) {
assigneesView.setOnClickListener(new ClickListener(getString(R.string.assignedTo, singleIssue.getAssignees().get(i).getFull_name()), ctx));
assigneesView.setOnClickListener(
new ClickListener(getString(R.string.assignedTo, singleIssue.getAssignees().get(i).getFull_name()), ctx));
}
else {
assigneesView.setOnClickListener(new ClickListener(getString(R.string.assignedTo, singleIssue.getAssignees().get(i).getLogin()), ctx));
assigneesView.setOnClickListener(
new ClickListener(getString(R.string.assignedTo, singleIssue.getAssignees().get(i).getLogin()), ctx));
}
}
@ -427,12 +464,13 @@ public class IssueDetailActivity extends BaseActivity {
assigneesScrollView.setVisibility(View.GONE);
}
LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT, LinearLayout.LayoutParams.WRAP_CONTENT);
LinearLayout.LayoutParams params = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.WRAP_CONTENT,
LinearLayout.LayoutParams.WRAP_CONTENT);
params.setMargins(0, 0, 15, 0);
if(singleIssue.getLabels() != null) {
labelsScrollView.setVisibility(View.VISIBLE);
int width = 25;
for(int i = 0; i < singleIssue.getLabels().size(); i++) {
String labelColor = singleIssue.getLabels().get(i).getColor();
@ -444,9 +482,15 @@ public class IssueDetailActivity extends BaseActivity {
labelsLayout.setGravity(Gravity.START | Gravity.TOP);
labelsView.setLayoutParams(params);
TextDrawable drawable = TextDrawable.builder().beginConfig().useFont(Typeface.DEFAULT).textColor(new ColorInverter().getContrastColor(color)).fontSize(30).width(LabelWidthCalculator.calculateLabelWidth(labelName, Typeface.DEFAULT, 30, 15)).height(50).endConfig().buildRoundRect(labelName, color, 10);
labelsView.setImageDrawable(drawable);
int height = AppUtil.getPixelsFromDensity(ctx, 25);
int textSize = AppUtil.getPixelsFromScaledDensity(ctx, 15);
TextDrawable drawable = TextDrawable.builder().beginConfig().useFont(Typeface.DEFAULT)
.textColor(new ColorInverter().getContrastColor(color)).fontSize(textSize)
.width(LabelWidthCalculator.calculateLabelWidth(labelName, Typeface.DEFAULT, textSize, AppUtil.getPixelsFromDensity(ctx, 10)))
.height(height).endConfig().buildRoundRect(labelName, color, AppUtil.getPixelsFromDensity(ctx, 5));
labelsView.setImageDrawable(drawable);
labelsLayout.addView(labelsView);
}
@ -461,7 +505,8 @@ public class IssueDetailActivity extends BaseActivity {
DateFormat formatter = new SimpleDateFormat("yyyy-MM-dd", new Locale(locale));
String dueDate = formatter.format(singleIssue.getDue_date());
issueDueDate.setText(dueDate);
issueDueDate.setOnClickListener(new ClickListener(TimeHelper.customDateFormatForToastDateFormat(singleIssue.getDue_date()), ctx));
issueDueDate
.setOnClickListener(new ClickListener(TimeHelper.customDateFormatForToastDateFormat(singleIssue.getDue_date()), ctx));
}
else if(timeFormat.equals("normal1")) {
DateFormat formatter = new SimpleDateFormat("dd-MM-yyyy", new Locale(locale));
@ -481,7 +526,8 @@ public class IssueDetailActivity extends BaseActivity {
edited = getString(R.string.colorfulBulletSpan) + getString(R.string.modifiedText);
issueModified.setVisibility(View.VISIBLE);
issueModified.setText(edited);
issueModified.setOnClickListener(new ClickListener(TimeHelper.customDateFormatForToastDateFormat(singleIssue.getUpdated_at()), ctx));
issueModified
.setOnClickListener(new ClickListener(TimeHelper.customDateFormatForToastDateFormat(singleIssue.getUpdated_at()), ctx));
}
else {
issueModified.setVisibility(View.INVISIBLE);
@ -508,7 +554,8 @@ public class IssueDetailActivity extends BaseActivity {
issueCreatedTime.setVisibility(View.VISIBLE);
if(timeFormat.equals("pretty")) {
issueCreatedTime.setOnClickListener(new ClickListener(TimeHelper.customDateFormatForToastDateFormat(singleIssue.getCreated_at()), ctx));
issueCreatedTime
.setOnClickListener(new ClickListener(TimeHelper.customDateFormatForToastDateFormat(singleIssue.getCreated_at()), ctx));
}
if(singleIssue.getMilestone() != null) {
@ -519,10 +566,12 @@ public class IssueDetailActivity extends BaseActivity {
}
if(!singleIssue.getUser().getFull_name().equals("")) {
assigneeAvatar.setOnClickListener(new ClickListener(ctx.getResources().getString(R.string.issueCreator) + singleIssue.getUser().getFull_name(), ctx));
assigneeAvatar.setOnClickListener(
new ClickListener(ctx.getResources().getString(R.string.issueCreator) + singleIssue.getUser().getFull_name(), ctx));
}
else {
assigneeAvatar.setOnClickListener(new ClickListener(ctx.getResources().getString(R.string.issueCreator) + singleIssue.getUser().getLogin(), ctx));
assigneeAvatar.setOnClickListener(
new ClickListener(ctx.getResources().getString(R.string.issueCreator) + singleIssue.getUser().getLogin(), ctx));
}
progressBar.setVisibility(View.GONE);
@ -531,7 +580,10 @@ public class IssueDetailActivity extends BaseActivity {
else if(response.code() == 401) {
AlertDialogs.authorizationTokenRevokedDialog(ctx, getResources().getString(R.string.alertDialogTokenRevokedTitle), getResources().getString(R.string.alertDialogTokenRevokedMessage), getResources().getString(R.string.alertDialogTokenRevokedCopyNegativeButton), getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
AlertDialogs.authorizationTokenRevokedDialog(ctx, getResources().getString(R.string.alertDialogTokenRevokedTitle),
getResources().getString(R.string.alertDialogTokenRevokedMessage),
getResources().getString(R.string.alertDialogTokenRevokedCopyNegativeButton),
getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
}
@ -547,7 +599,8 @@ public class IssueDetailActivity extends BaseActivity {
if(new Version(tinyDb.getString("giteaVersion")).higherOrEqual("1.12.0")) {
Call<WatchInfo> call2 = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().checkIssueWatchStatus(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, issueIndex);
Call<WatchInfo> call2 = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface()
.checkIssueWatchStatus(Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, issueIndex);
call2.enqueue(new Callback<WatchInfo>() {

View File

@ -10,41 +10,59 @@ import android.graphics.Typeface;
import android.net.Uri;
import android.os.Bundle;
import android.util.Log;
import android.view.Menu;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.app.ActionBarDrawerToggle;
import androidx.appcompat.app.AlertDialog;
import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.widget.Toolbar;
import androidx.core.view.GravityCompat;
import androidx.drawerlayout.widget.DrawerLayout;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager;
import androidx.recyclerview.widget.RecyclerView;
import com.google.android.material.navigation.NavigationView;
import com.squareup.picasso.NetworkPolicy;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.UserAccountsNavAdapter;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.UserAccountsApi;
import org.mian.gitnex.database.models.UserAccount;
import org.mian.gitnex.fragments.AboutFragment;
import org.mian.gitnex.fragments.AdministrationFragment;
import org.mian.gitnex.fragments.BottomSheetDraftsFragment;
import org.mian.gitnex.fragments.DraftsFragment;
import org.mian.gitnex.fragments.ExploreRepositoriesFragment;
import org.mian.gitnex.fragments.MyRepositoriesFragment;
import org.mian.gitnex.fragments.NotificationsFragment;
import org.mian.gitnex.fragments.OrganizationsFragment;
import org.mian.gitnex.fragments.ProfileFragment;
import org.mian.gitnex.fragments.RepositoriesFragment;
import org.mian.gitnex.fragments.SettingsFragment;
import org.mian.gitnex.fragments.StarredRepositoriesFragment;
import org.mian.gitnex.fragments.UserAccountsFragment;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.ChangeLog;
import org.mian.gitnex.helpers.ColorInverter;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.GiteaVersion;
import org.mian.gitnex.models.NotificationCount;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import eightbitlab.com.blurview.BlurView;
import eightbitlab.com.blurview.RenderScriptBlur;
import retrofit2.Call;
import retrofit2.Callback;
@ -52,17 +70,28 @@ import retrofit2.Callback;
* Author M M Arif
*/
public class MainActivity extends BaseActivity implements NavigationView.OnNavigationItemSelectedListener {
public class MainActivity extends BaseActivity implements NavigationView.OnNavigationItemSelectedListener, BottomSheetDraftsFragment.BottomSheetListener {
private DrawerLayout drawer;
private BlurView blurView;
private TextView userFullName;
private TextView userEmail;
private ImageView userAvatar;
private ImageView userAvatarBackground;
private ViewGroup navHeaderFrame;
private TextView toolbarTitle;
final Context ctx = this;
private Context appCtx;
private Typeface myTypeface;
private String instanceUrl;
private String loginUid;
private String instanceToken;
private View hView;
private MenuItem navNotifications;
private TextView notificationCounter;
@Override
protected int getLayoutResourceId() {
@ -77,11 +106,13 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
final TinyDB tinyDb = new TinyDB(appCtx);
tinyDb.putBoolean("noConnection", false);
//userAvatar = findViewById(R.id.userAvatar);
final String instanceUrl = tinyDb.getString("instanceUrl");
final String loginUid = tinyDb.getString("loginUid");
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
Intent mainIntent = getIntent();
String launchFragment = mainIntent.getStringExtra("launchFragment");
instanceUrl = tinyDb.getString("instanceUrl");
loginUid = tinyDb.getString("loginUid");
instanceToken = "token " + tinyDb.getString(loginUid + "-token");
if(tinyDb.getString("dateFormat").isEmpty()) {
tinyDb.putString("dateFormat", "pretty");
@ -100,13 +131,17 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
tinyDb.putInt("homeScreenId", 0);
}
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
if(!tinyDb.getBoolean("loggedInMode")) {
logout(this, ctx);
return;
}
if(tinyDb.getInt("currentActiveAccountId") <= 0) {
AlertDialogs.forceLogoutDialog(ctx, getResources().getString(R.string.forceLogoutDialogHeader), getResources().getString(R.string.forceLogoutDialogDescription), getResources().getString(R.string.alertDialogTokenRevokedCopyPositiveButton));
}
Toolbar toolbar = findViewById(R.id.toolbar);
toolbarTitle = toolbar.findViewById(R.id.toolbar_title);
@ -131,6 +166,7 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
FragmentManager fm = getSupportFragmentManager();
Fragment fragmentById = fm.findFragmentById(R.id.fragment_container);
if(fragmentById instanceof SettingsFragment) {
toolbarTitle.setText(getResources().getString(R.string.pageTitleSettings));
}
@ -146,37 +182,51 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
else if(fragmentById instanceof ExploreRepositoriesFragment) {
toolbarTitle.setText(getResources().getString(R.string.pageTitleExplore));
}
else if(fragmentById instanceof NotificationsFragment) {
toolbarTitle.setText(R.string.pageTitleNotifications);
}
else if(fragmentById instanceof ProfileFragment) {
toolbarTitle.setText(getResources().getString(R.string.pageTitleProfile));
}
else if(fragmentById instanceof AboutFragment) {
toolbarTitle.setText(getResources().getString(R.string.pageTitleAbout));
}
else if(fragmentById instanceof DraftsFragment) {
toolbarTitle.setText(getResources().getString(R.string.titleDrafts));
}
else if(fragmentById instanceof AdministrationFragment) {
toolbarTitle.setText(getResources().getString(R.string.pageTitleAdministration));
}
else if(fragmentById instanceof UserAccountsFragment) {
toolbarTitle.setText(getResources().getString(R.string.pageTitleUserAccounts));
}
getNotificationsCount(instanceUrl, instanceToken);
drawer = findViewById(R.id.drawer_layout);
NavigationView navigationView = findViewById(R.id.nav_view);
navigationView.setNavigationItemSelectedListener(this);
final View hView = navigationView.getHeaderView(0);
hView = navigationView.getHeaderView(0);
Menu menu = navigationView.getMenu();
navNotifications = menu.findItem(R.id.nav_notifications);
ActionBarDrawerToggle toggle = new ActionBarDrawerToggle(this, drawer, toolbar, R.string.navigation_drawer_open, R.string.navigation_drawer_close);
toggle.getDrawerArrowDrawable().setColor(getResources().getColor(R.color.darkGreen));
drawer.addDrawerListener(toggle);
drawer.addDrawerListener(new DrawerLayout.DrawerListener() {
@Override
public void onDrawerSlide(@NonNull View drawerView, float slideOffset) {
}
@Override
public void onDrawerOpened(@NonNull View drawerView) {
getNotificationsCount(instanceUrl, instanceToken);
}
@Override
public void onDrawerSlide(@NonNull View drawerView, float slideOffset) {
if(tinyDb.getBoolean("noConnection")) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
tinyDb.putBoolean("noConnection", false);
}
@ -184,84 +234,191 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
String userFullNameNav = tinyDb.getString("userFullname");
String userAvatarNav = tinyDb.getString("userAvatar");
blurView = hView.findViewById(R.id.blurView);
userEmail = hView.findViewById(R.id.userEmail);
userFullName = hView.findViewById(R.id.userFullname);
userAvatar = hView.findViewById(R.id.userAvatar);
userAvatarBackground = hView.findViewById(R.id.userAvatarBackground);
navHeaderFrame = hView.findViewById(R.id.navHeaderFrame);
List<UserAccount> userAccountsList;
userAccountsList = new ArrayList<>();
UserAccountsApi userAccountsApi;
userAccountsApi = new UserAccountsApi(ctx);
RecyclerView navRecyclerViewUserAccounts = hView.findViewById(R.id.navRecyclerViewUserAccounts);
UserAccountsNavAdapter adapterUserAccounts;
adapterUserAccounts = new UserAccountsNavAdapter(ctx, userAccountsList, drawer, toolbarTitle);
userAccountsApi.getAllAccounts().observe((AppCompatActivity) ctx, userAccounts -> {
if(userAccounts.size() > 0) {
userAccountsList.addAll(userAccounts);
navRecyclerViewUserAccounts.setAdapter(adapterUserAccounts);
}
});
userEmail.setTypeface(myTypeface);
userFullName.setTypeface(myTypeface);
if(!userEmailNav.equals("")) {
userEmail.setText(userEmailNav);
userEmail.setTypeface(myTypeface);
}
userFullName = hView.findViewById(R.id.userFullname);
if(!userFullNameNav.equals("")) {
userFullName.setText(userFullNameNav);
userFullName.setTypeface(myTypeface);
}
userAvatar = hView.findViewById(R.id.userAvatar);
if(!userAvatarNav.equals("")) {
PicassoService.getInstance(ctx).get().load(userAvatarNav).networkPolicy(NetworkPolicy.OFFLINE).placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(160, 160).centerCrop().into(userAvatar);
PicassoService.getInstance(ctx).get()
.load(userAvatarNav)
.placeholder(R.drawable.loader_animated)
.transform(new RoundedTransformation(8, 0))
.resize(160, 160)
.centerCrop().into(userAvatar);
PicassoService.getInstance(ctx).get()
.load(userAvatarNav)
.into(userAvatarBackground, new com.squareup.picasso.Callback() {
@Override
public void onSuccess() {
int textColor = new ColorInverter().getImageViewContrastColor(userAvatarBackground);
userFullName.setTextColor(textColor);
userEmail.setTextColor(textColor);
blurView.setupWith(navHeaderFrame)
.setBlurAlgorithm(new RenderScriptBlur(ctx))
.setBlurRadius(5)
.setHasFixedTransformationMatrix(false);
}
userAvatar.setOnClickListener(new View.OnClickListener() {
@Override
public void onError(Exception e) {}
public void onClick(View v) {
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new ProfileFragment()).commit();
drawer.closeDrawers();
}
});
}
@Override
public void onDrawerClosed(@NonNull View drawerView) {
// Called when a drawer has settled in a completely closed state.
userAvatar.setOnClickListener(v -> {
toolbarTitle.setText(getResources().getString(R.string.pageTitleProfile));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new ProfileFragment()).commit();
drawer.closeDrawers();
});
String currentVersion = tinyDb.getString("giteaVersion");
navigationView.getMenu().findItem(R.id.nav_administration).setVisible(tinyDb.getBoolean("userIsAdmin"));
navigationView.getMenu().findItem(R.id.nav_notifications).setVisible(new Version(currentVersion).higherOrEqual("1.12.3"));
}
@Override
public void onDrawerStateChanged(int newState) {
// Called when the drawer motion state changes. The new state will be one of STATE_IDLE, STATE_DRAGGING or STATE_SETTLING.
}
public void onDrawerClosed(@NonNull View drawerView) {}
@Override
public void onDrawerStateChanged(int newState) {}
});
toggle.syncState();
toolbar.setNavigationIcon(R.drawable.ic_menu);
if(launchFragment != null) {
mainIntent.removeExtra("launchFragment");
switch(launchFragment) {
case "drafts":
toolbarTitle.setText(getResources().getString(R.string.titleDrafts));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new DraftsFragment()).commit();
navigationView.setCheckedItem(R.id.nav_comments_draft);
return;
case "notifications":
toolbarTitle.setText(getResources().getString(R.string.pageTitleNotifications));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new NotificationsFragment()).commit();
navigationView.setCheckedItem(R.id.nav_notifications);
return;
}
}
if(savedInstanceState == null) {
if(tinyDb.getInt("homeScreenId") == 0) {
toolbarTitle.setText(getResources().getString(R.string.pageTitleMyRepos));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new MyRepositoriesFragment()).commit();
navigationView.setCheckedItem(R.id.nav_home);
if(!new Version(tinyDb.getString("giteaVersion")).higherOrEqual("1.12.3")) {
if(tinyDb.getInt("homeScreenId") == 7) {
tinyDb.putInt("homeScreenId", 0);
}
else if(tinyDb.getInt("homeScreenId") == 1) {
}
switch(tinyDb.getInt("homeScreenId")) {
case 1:
toolbarTitle.setText(getResources().getString(R.string.pageTitleStarredRepos));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new StarredRepositoriesFragment()).commit();
navigationView.setCheckedItem(R.id.nav_starred_repos);
}
else if(tinyDb.getInt("homeScreenId") == 2) {
break;
case 2:
toolbarTitle.setText(getResources().getString(R.string.pageTitleOrganizations));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new OrganizationsFragment()).commit();
navigationView.setCheckedItem(R.id.nav_organizations);
}
else if(tinyDb.getInt("homeScreenId") == 3) {
break;
case 3:
toolbarTitle.setText(getResources().getString(R.string.pageTitleRepositories));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new RepositoriesFragment()).commit();
navigationView.setCheckedItem(R.id.nav_repositories);
}
else if(tinyDb.getInt("homeScreenId") == 4) {
break;
case 4:
toolbarTitle.setText(getResources().getString(R.string.pageTitleProfile));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new ProfileFragment()).commit();
navigationView.setCheckedItem(R.id.nav_profile);
}
else {
break;
case 5:
toolbarTitle.setText(getResources().getString(R.string.pageTitleExplore));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new ExploreRepositoriesFragment()).commit();
navigationView.setCheckedItem(R.id.nav_explore);
break;
case 6:
toolbarTitle.setText(getResources().getString(R.string.titleDrafts));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new DraftsFragment()).commit();
navigationView.setCheckedItem(R.id.nav_comments_draft);
break;
case 7:
toolbarTitle.setText(getResources().getString(R.string.pageTitleNotifications));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new NotificationsFragment()).commit();
navigationView.setCheckedItem(R.id.nav_notifications);
break;
default:
toolbarTitle.setText(getResources().getString(R.string.pageTitleMyRepos));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new MyRepositoriesFragment()).commit();
navigationView.setCheckedItem(R.id.nav_home);
break;
}
}
if(!connToInternet) {
if(!tinyDb.getBoolean("noConnection")) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
}
tinyDb.putBoolean("noConnection", true);
@ -269,7 +426,7 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
}
else {
displayUserInfo(instanceUrl, instanceToken, loginUid);
loadUserInfo(instanceUrl, instanceToken, loginUid);
giteaVersion(instanceUrl);
tinyDb.putBoolean("noConnection", false);
@ -277,25 +434,67 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
// Changelog popup
int versionCode = 0;
try {
PackageInfo packageInfo = appCtx.getPackageManager().getPackageInfo(appCtx.getPackageName(), 0);
versionCode = packageInfo.versionCode;
}
catch(PackageManager.NameNotFoundException e) {
Log.e("changelogDialog", Objects.requireNonNull(e.getMessage()));
}
if(versionCode > tinyDb.getInt("versionCode")) {
tinyDb.putInt("versionCode", versionCode);
tinyDb.putBoolean("versionFlag", true);
ChangeLog changelogDialog = new ChangeLog(this);
changelogDialog.showDialog();
}
}
public void setActionBarTitle(@NonNull String title) {
@Override
public void onButtonClicked(String text) {
TinyDB tinyDb = new TinyDB(ctx);
int currentActiveAccountId = tinyDb.getInt("currentActiveAccountId");
if("deleteDrafts".equals(text)) {
if(currentActiveAccountId > 0) {
FragmentManager fm = getSupportFragmentManager();
DraftsFragment frag = (DraftsFragment) fm.findFragmentById(R.id.fragment_container);
if(frag != null) {
new AlertDialog.Builder(ctx)
.setTitle(R.string.deleteAllDrafts)
.setIcon(R.drawable.ic_delete)
.setCancelable(false)
.setMessage(R.string.deleteAllDraftsDialogMessage)
.setPositiveButton(R.string.menuDeleteText, (dialog, which) -> {
frag.deleteAllDrafts(currentActiveAccountId);
dialog.dismiss();
})
.setNeutralButton(R.string.cancelButton, null).show();
}
else {
Toasty.error(ctx, getResources().getString(R.string.genericError));
}
}
else {
Toasty.error(ctx, getResources().getString(R.string.genericError));
}
}
Objects.requireNonNull(getSupportActionBar()).setTitle(title);
}
@Override
@ -314,46 +513,66 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
public boolean onNavigationItemSelected(@NonNull MenuItem menuItem) {
switch(menuItem.getItemId()) {
case R.id.nav_home:
toolbarTitle.setText(getResources().getString(R.string.pageTitleMyRepos));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new MyRepositoriesFragment()).commit();
break;
case R.id.nav_organizations:
toolbarTitle.setText(getResources().getString(R.string.pageTitleOrganizations));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new OrganizationsFragment()).commit();
break;
case R.id.nav_profile:
toolbarTitle.setText(getResources().getString(R.string.pageTitleProfile));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new ProfileFragment()).commit();
break;
case R.id.nav_repositories:
toolbarTitle.setText(getResources().getString(R.string.pageTitleRepositories));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new RepositoriesFragment()).commit();
break;
case R.id.nav_settings:
toolbarTitle.setText(getResources().getString(R.string.pageTitleSettings));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new SettingsFragment()).commit();
break;
case R.id.nav_logout:
logout(this, ctx);
overridePendingTransition(android.R.anim.fade_in, android.R.anim.fade_out);
break;
case R.id.nav_about:
toolbarTitle.setText(getResources().getString(R.string.pageTitleAbout));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new AboutFragment()).commit();
break;
case R.id.nav_rate_app:
rateThisApp();
break;
case R.id.nav_starred_repos:
toolbarTitle.setText(getResources().getString(R.string.pageTitleStarredRepos));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new StarredRepositoriesFragment()).commit();
break;
case R.id.nav_explore:
toolbarTitle.setText(getResources().getString(R.string.pageTitleExplore));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new ExploreRepositoriesFragment()).commit();
break;
case R.id.nav_notifications:
toolbarTitle.setText(R.string.pageTitleNotifications);
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new NotificationsFragment()).commit();
break;
case R.id.nav_comments_draft:
toolbarTitle.setText(getResources().getString(R.string.titleDrafts));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new DraftsFragment()).commit();
break;
case R.id.nav_administration:
toolbarTitle.setText(getResources().getString(R.string.pageTitleAdministration));
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new AdministrationFragment()).commit();
@ -387,6 +606,21 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
int id = item.getItemId();
if(id == R.id.genericMenu) {
BottomSheetDraftsFragment bottomSheet = new BottomSheetDraftsFragment();
bottomSheet.show(getSupportFragmentManager(), "draftsBottomSheet");
return true;
}
return super.onOptionsItemSelected(item);
}
private void giteaVersion(final String instanceUrl) {
final TinyDB tinyDb = new TinyDB(appCtx);
@ -408,29 +642,24 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
tinyDb.putString("giteaVersion", version.getVersion());
}
}
@Override
public void onFailure(@NonNull Call<GiteaVersion> callVersion, @NonNull Throwable t) {
Log.e("onFailure-version", t.toString());
}
});
}
private void displayUserInfo(String instanceUrl, String token, String loginUid) {
private void loadUserInfo(String instanceUrl, String token, String loginUid) {
final TinyDB tinyDb = new TinyDB(appCtx);
Call<UserInfo> call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().getUserInfo(Authorization.returnAuthentication(ctx, loginUid, token));
NavigationView navigationView = findViewById(R.id.nav_view);
final View hView = navigationView.getHeaderView(0);
call.enqueue(new Callback<UserInfo>() {
@Override
@ -443,12 +672,14 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
if(response.code() == 200) {
assert userDetails != null;
if(userDetails.getIs_admin() != null) {
tinyDb.putBoolean("userIsAdmin", userDetails.getIs_admin());
navigationView.getMenu().findItem(R.id.nav_administration).setVisible(userDetails.getIs_admin());
}
tinyDb.putString("userLogin", userDetails.getLogin());
tinyDb.putInt("userId", userDetails.getId());
if(!userDetails.getFullname().equals("")) {
tinyDb.putString("userFullname", userDetails.getFullname());
}
@ -458,51 +689,14 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
tinyDb.putString("userEmail", userDetails.getEmail());
tinyDb.putString("userAvatar", userDetails.getAvatar());
if(userDetails.getLang() != null) {
tinyDb.putString("userLang", userDetails.getLang());
}
else {
tinyDb.putString("userLang", "...");
tinyDb.putString("userLang", "");
}
userAvatar = hView.findViewById(R.id.userAvatar);
if(!Objects.requireNonNull(userDetails).getAvatar().equals("")) {
PicassoService.getInstance(ctx).get().load(userDetails.getAvatar()).placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(160, 160).centerCrop().into(userAvatar);
}
else {
userAvatar.setImageResource(R.mipmap.app_logo_round);
}
userFullName = hView.findViewById(R.id.userFullname);
if(!userDetails.getFullname().equals("")) {
userFullName.setText(userDetails.getFullname());
}
else if(!userDetails.getLogin().equals("")) {
userFullName.setText(userDetails.getLogin());
}
else {
userFullName.setText("...");
}
userEmail = hView.findViewById(R.id.userEmail);
if(!userDetails.getEmail().equals("")) {
userEmail.setText(userDetails.getEmail());
}
else {
userEmail.setText("...");
}
userAvatar.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new ProfileFragment()).commit();
drawer.closeDrawers();
}
});
}
}
else if(response.code() == 401) {
@ -511,8 +705,8 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
}
else {
String toastError = getResources().getString(R.string.genericApiStatusError) + String.valueOf(response.code());
Toasty.info(ctx, toastError);
String toastError = getResources().getString(R.string.genericApiStatusError) + response.code();
Toasty.error(ctx, toastError);
}
@ -527,4 +721,31 @@ public class MainActivity extends BaseActivity implements NavigationView.OnNavig
}
private void getNotificationsCount(String instanceUrl, String token) {
Call<NotificationCount> call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().checkUnreadNotifications(token);
call.enqueue(new Callback<NotificationCount>() {
@Override
public void onResponse(@NonNull Call<NotificationCount> call, @NonNull retrofit2.Response<NotificationCount> response) {
NotificationCount notificationCount = response.body();
if(response.code() == 200) {
assert notificationCount != null;
notificationCounter = navNotifications.getActionView().findViewById(R.id.counterBadgeNotification);
notificationCounter.setText(String.valueOf(notificationCount.getCounter()));
}
}
@Override
public void onFailure(@NonNull Call<NotificationCount> call, @NonNull Throwable t) {
Log.e("onFailure-notification", t.toString());
}
});
}
}

View File

@ -16,14 +16,14 @@ import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.databinding.ActivityMergePullRequestBinding;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.Collaborators;
import org.mian.gitnex.models.MergePullRequest;
import org.mian.gitnex.models.MergePullRequestSpinner;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import okhttp3.ResponseBody;
@ -62,7 +62,7 @@ public class MergePullRequestActivity extends BaseActivity {
View view = viewBinding.getRoot();
setContentView(view);
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
TinyDB tinyDb = new TinyDB(appCtx);
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
@ -126,12 +126,10 @@ public class MergePullRequestActivity extends BaseActivity {
if(!connToInternet) {
disableProcessButton();
}
else {
viewBinding.mergeButton.setOnClickListener(mergePullRequest);
}
}
@ -217,11 +215,11 @@ public class MergePullRequestActivity extends BaseActivity {
String mergePRTitle = viewBinding.mergeTitle.getText().toString();
boolean deleteBranch = viewBinding.deleteBranch.isChecked();
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
@ -266,7 +264,7 @@ public class MergePullRequestActivity extends BaseActivity {
deleteBranchFunction(repoOwner, repoName);
Toasty.info(ctx, getString(R.string.mergePRSuccessMsg));
Toasty.success(ctx, getString(R.string.mergePRSuccessMsg));
tinyDb.putBoolean("prMerged", true);
tinyDb.putBoolean("resumePullRequests", true);
finish();
@ -281,7 +279,7 @@ public class MergePullRequestActivity extends BaseActivity {
deleteBranchFunction(repoOwner, repoName);
Toasty.info(ctx, getString(R.string.mergePRSuccessMsg));
Toasty.success(ctx, getString(R.string.mergePRSuccessMsg));
tinyDb.putBoolean("prMerged", true);
tinyDb.putBoolean("resumePullRequests", true);
finish();
@ -291,7 +289,7 @@ public class MergePullRequestActivity extends BaseActivity {
}
else {
Toasty.info(ctx, getString(R.string.mergePRSuccessMsg));
Toasty.success(ctx, getString(R.string.mergePRSuccessMsg));
tinyDb.putBoolean("prMerged", true);
tinyDb.putBoolean("resumePullRequests", true);
finish();
@ -308,13 +306,13 @@ public class MergePullRequestActivity extends BaseActivity {
else if(response.code() == 404) {
enableProcessButton();
Toasty.info(ctx, getString(R.string.mergePR404ErrorMsg));
Toasty.warning(ctx, getString(R.string.mergePR404ErrorMsg));
}
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.genericError));
Toasty.error(ctx, getString(R.string.genericError));
}
@ -373,15 +371,11 @@ public class MergePullRequestActivity extends BaseActivity {
private void disableProcessButton() {
viewBinding.mergeButton.setEnabled(false);
viewBinding.mergeButton.setBackground(getResources().getDrawable(R.drawable.shape_buttons_disabled));
}
private void enableProcessButton() {
viewBinding.mergeButton.setEnabled(true);
viewBinding.mergeButton.setBackground(getResources().getDrawable(R.drawable.shape_buttons));
}
}

View File

@ -5,7 +5,13 @@ import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
import androidx.appcompat.app.AppCompatActivity;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.PathsHelper;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import java.net.URI;
import java.net.URISyntaxException;
import io.mikael.urlbuilder.UrlBuilder;
/**
* Author M M Arif
@ -20,19 +26,29 @@ public class OpenRepoInBrowserActivity extends AppCompatActivity {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
TinyDB tinyDb = new TinyDB(appCtx);
String instanceUrlWithProtocol = "https://" + tinyDb.getString("instanceUrlRaw");
if (!tinyDb.getString("instanceUrlWithProtocol").isEmpty()) {
instanceUrlWithProtocol = tinyDb.getString("instanceUrlWithProtocol");
}
String repoFullNameBrowser = getIntent().getStringExtra("repoFullNameBrowser");
Uri url = Uri.parse(instanceUrlWithProtocol + "/" + repoFullNameBrowser);
Intent i = new Intent(Intent.ACTION_VIEW, url);
try {
URI instanceUrl = new URI(UrlBuilder.fromString(tinyDb.getString("instanceUrl"))
.withPath("/")
.toString());
String browserPath = PathsHelper.join(instanceUrl.getPath(), getIntent().getStringExtra("repoFullNameBrowser"));
String browserUrl = UrlBuilder.fromUri(instanceUrl)
.withPath(browserPath)
.toString();
Intent i = new Intent(Intent.ACTION_VIEW, Uri.parse(browserUrl));
startActivity(i);
finish();
}
catch(URISyntaxException e) {
Toasty.error(appCtx, getString(R.string.genericError));
}
}
}

View File

@ -1,12 +1,7 @@
package org.mian.gitnex.activities;
import com.google.android.material.tabs.TabLayout;
import androidx.annotation.NonNull;
import androidx.appcompat.widget.Toolbar;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager;
import androidx.fragment.app.FragmentPagerAdapter;
import androidx.viewpager.widget.ViewPager;
import android.content.ClipData;
import android.content.ClipboardManager;
import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
@ -17,14 +12,23 @@ import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.widget.Toolbar;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager;
import androidx.fragment.app.FragmentPagerAdapter;
import androidx.viewpager.widget.ViewPager;
import com.google.android.material.tabs.TabLayout;
import org.mian.gitnex.R;
import org.mian.gitnex.fragments.MembersByOrgFragment;
import org.mian.gitnex.fragments.BottomSheetOrganizationFragment;
import org.mian.gitnex.fragments.MembersByOrgFragment;
import org.mian.gitnex.fragments.OrganizationInfoFragment;
import org.mian.gitnex.fragments.RepositoriesByOrgFragment;
import org.mian.gitnex.fragments.TeamsByOrgFragment;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import java.util.Objects;
import io.mikael.urlbuilder.UrlBuilder;
/**
* Author M M Arif
@ -34,6 +38,7 @@ public class OrganizationDetailActivity extends BaseActivity implements BottomSh
final Context ctx = this;
private Context appCtx;
private TinyDB tinyDb;
@Override
protected int getLayoutResourceId(){
@ -45,6 +50,7 @@ public class OrganizationDetailActivity extends BaseActivity implements BottomSh
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
tinyDb = new TinyDB(appCtx);
TinyDB tinyDb = new TinyDB(appCtx);
String orgName = tinyDb.getString("orgName");
@ -105,6 +111,7 @@ public class OrganizationDetailActivity extends BaseActivity implements BottomSh
@Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.repo_dotted_menu, menu);
return true;
@ -132,19 +139,28 @@ public class OrganizationDetailActivity extends BaseActivity implements BottomSh
@Override
public void onButtonClicked(String text) {
TinyDB tinyDb = new TinyDB(appCtx);
switch (text) {
case "repository":
tinyDb.putBoolean("organizationAction", true);
startActivity(new Intent(OrganizationDetailActivity.this, CreateRepoActivity.class));
break;
case "team":
startActivity(new Intent(OrganizationDetailActivity.this, CreateTeamByOrgActivity.class));
break;
}
//Log.i("clicked", text);
case "copyOrgUrl":
String url = UrlBuilder.fromString(tinyDb.getString("instanceUrl"))
.withPath("/")
.toString();
ClipboardManager clipboard = (ClipboardManager) Objects.requireNonNull(ctx).getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText("orgUrl", url + tinyDb.getString("orgName"));
assert clipboard != null;
clipboard.setPrimaryClip(clip);
Toasty.info(ctx, ctx.getString(R.string.copyIssueUrlToastMsg));
break;
}
}
public class SectionsPagerAdapter extends FragmentPagerAdapter {
@ -157,7 +173,6 @@ public class OrganizationDetailActivity extends BaseActivity implements BottomSh
@Override
public Fragment getItem(int position) {
TinyDB tinyDb = new TinyDB(appCtx);
String orgName;
if(getIntent().getStringExtra("orgName") != null || !Objects.equals(getIntent().getStringExtra("orgName"), "")) {
orgName = getIntent().getStringExtra("orgName");

View File

@ -9,6 +9,7 @@ import android.view.MenuItem;
import android.view.View;
import android.widget.GridView;
import android.widget.ImageView;
import android.widget.ProgressBar;
import android.widget.TextView;
import androidx.appcompat.widget.Toolbar;
import androidx.lifecycle.ViewModelProvider;
@ -16,7 +17,7 @@ import org.mian.gitnex.R;
import org.mian.gitnex.adapters.TeamMembersByOrgAdapter;
import org.mian.gitnex.fragments.BottomSheetOrganizationTeamsFragment;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.viewmodels.TeamMembersByOrgViewModel;
import java.util.Objects;
@ -30,6 +31,7 @@ public class OrganizationTeamMembersActivity extends BaseActivity implements Bot
private View.OnClickListener onClickListener;
private TeamMembersByOrgAdapter adapter;
private GridView mGridView;
private ProgressBar progressBar;
final Context ctx = this;
private Context appCtx;
@ -58,6 +60,7 @@ public class OrganizationTeamMembersActivity extends BaseActivity implements Bot
TextView toolbarTitle = findViewById(R.id.toolbar_title);
noDataMembers = findViewById(R.id.noDataMembers);
mGridView = findViewById(R.id.gridView);
progressBar = findViewById(R.id.progressBar);
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
@ -114,6 +117,7 @@ public class OrganizationTeamMembersActivity extends BaseActivity implements Bot
noDataMembers.setVisibility(View.VISIBLE);
}
progressBar.setVisibility(View.GONE);
});
}

View File

@ -1,10 +1,6 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import retrofit2.Call;
import retrofit2.Callback;
import android.content.Context;
import android.graphics.drawable.GradientDrawable;
import android.os.Bundle;
import android.util.Log;
import android.util.Patterns;
@ -13,18 +9,21 @@ import android.view.inputmethod.InputMethodManager;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import androidx.annotation.NonNull;
import com.google.gson.JsonElement;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.AddEmail;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
@ -49,7 +48,7 @@ public class ProfileEmailActivity extends BaseActivity {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
@ -67,11 +66,9 @@ public class ProfileEmailActivity extends BaseActivity {
if(!connToInternet) {
disableProcessButton();
} else {
addEmailButton.setOnClickListener(addEmailListener);
}
}
@ -84,7 +81,7 @@ public class ProfileEmailActivity extends BaseActivity {
private void processAddNewEmail() {
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
final String loginUid = tinyDb.getString("loginUid");
@ -94,20 +91,20 @@ public class ProfileEmailActivity extends BaseActivity {
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if(newUserEmail.equals("")) {
Toasty.info(ctx, getString(R.string.emailErrorEmpty));
Toasty.error(ctx, getString(R.string.emailErrorEmpty));
return;
}
else if(!Patterns.EMAIL_ADDRESS.matcher(newUserEmail).matches()) {
Toasty.info(ctx, getString(R.string.emailErrorInvalid));
Toasty.warning(ctx, getString(R.string.emailErrorInvalid));
return;
}
@ -138,7 +135,7 @@ public class ProfileEmailActivity extends BaseActivity {
if(response.code() == 201) {
Toasty.info(ctx, getString(R.string.emailAddedText));
Toasty.success(ctx, getString(R.string.emailAddedText));
tinyDb.putBoolean("emailsRefresh", true);
enableProcessButton();
finish();
@ -156,25 +153,25 @@ public class ProfileEmailActivity extends BaseActivity {
else if(response.code() == 403) {
enableProcessButton();
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
enableProcessButton();
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else if(response.code() == 422) {
enableProcessButton();
Toasty.info(ctx, ctx.getString(R.string.emailErrorInUse));
Toasty.warning(ctx, ctx.getString(R.string.emailErrorInUse));
}
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.labelGeneralError));
Toasty.error(ctx, getString(R.string.labelGeneralError));
}
@ -190,32 +187,18 @@ public class ProfileEmailActivity extends BaseActivity {
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
onClickListener = view -> finish();
}
private void disableProcessButton() {
addEmailButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
addEmailButton.setBackground(shape);
}
private void enableProcessButton() {
addEmailButton.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
addEmailButton.setBackground(shape);
}
}

View File

@ -1,33 +1,42 @@
package org.mian.gitnex.activities;
import androidx.annotation.NonNull;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import android.content.Context;
import android.graphics.drawable.GradientDrawable;
import android.content.Intent;
import android.os.Bundle;
import android.text.Editable;
import android.text.TextWatcher;
import android.util.Log;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.inputmethod.InputMethodManager;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.widget.Toolbar;
import com.hendraanggrian.appcompat.socialview.Mention;
import com.hendraanggrian.appcompat.widget.MentionArrayAdapter;
import com.hendraanggrian.appcompat.widget.SocialAutoCompleteTextView;
import org.mian.gitnex.R;
import org.mian.gitnex.actions.IssueActions;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.DraftsApi;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.StaticGlobalVariables;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.Collaborators;
import org.mian.gitnex.models.Issues;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
import java.util.Objects;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
/**
* Author M M Arif
@ -41,9 +50,12 @@ public class ReplyToIssueActivity extends BaseActivity {
final Context ctx = this;
private Context appCtx;
private TextView draftSaved;
private SocialAutoCompleteTextView addComment;
private ArrayAdapter<Mention> defaultMentionAdapter;
private Button replyButton;
private String TAG = StaticGlobalVariables.replyToIssueActivity;
private long draftIdOnCreate;
@Override
protected int getLayoutResourceId(){
@ -55,16 +67,19 @@ public class ReplyToIssueActivity extends BaseActivity {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
Toolbar toolbar = findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
TinyDB tinyDb = new TinyDB(appCtx);
draftSaved = findViewById(R.id.draftSaved);
addComment = findViewById(R.id.addComment);
addComment.setShowSoftInputOnFocus(true);
defaultMentionAdapter = new MentionArrayAdapter<>(this);
defaultMentionAdapter = new MentionArrayAdapter<>(ctx);
loadCollaboratorsList();
addComment.setMentionAdapter(defaultMentionAdapter);
@ -83,6 +98,20 @@ public class ReplyToIssueActivity extends BaseActivity {
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
if(getIntent().getStringExtra("draftId") != null) {
draftIdOnCreate = Long.parseLong(Objects.requireNonNull(getIntent().getStringExtra("draftId")));
}
else {
if(getIntent().getStringExtra("commentBody") != null) {
draftIdOnCreate = returnDraftId(getIntent().getStringExtra("commentBody"));
}
else {
draftIdOnCreate = returnDraftId("");
}
}
replyButton = findViewById(R.id.replyButton);
if(getIntent().getStringExtra("commentBody") != null) {
@ -95,27 +124,75 @@ public class ReplyToIssueActivity extends BaseActivity {
}
if(getIntent().getStringExtra("commentAction") != null && getIntent().getStringExtra("commentAction").equals("edit")) {
if(getIntent().getStringExtra("draftTitle") != null) {
toolbar_title.setText(getIntent().getStringExtra("draftTitle"));
}
if(getIntent().getStringExtra("commentAction") != null && Objects.equals(getIntent().getStringExtra("commentAction"), "edit") && !Objects.equals(getIntent().getStringExtra("commentId"), "new")) {
final String commentId = getIntent().getStringExtra("commentId");
toolbar_title.setText(getResources().getString(R.string.editCommentTitle));
replyButton.setText(getResources().getString(R.string.editCommentButtonText));
addComment.addTextChangedListener(new TextWatcher() {
public void afterTextChanged(Editable s) {
}
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
public void onTextChanged(CharSequence s, int start, int before, int count) {
saveDraft(addComment.getText().toString(), commentId, draftIdOnCreate);
draftSaved.setVisibility(View.VISIBLE);
}
});
replyButton.setOnClickListener(v -> {
disableProcessButton();
IssueActions.editIssueComment(ctx, Integer.parseInt(commentId), addComment.getText().toString());
assert commentId != null;
IssueActions.editIssueComment(ctx, Integer.parseInt(commentId), addComment.getText().toString(), draftIdOnCreate);
});
return;
}
addComment.addTextChangedListener(new TextWatcher() {
public void afterTextChanged(Editable s) {
}
public void beforeTextChanged(CharSequence s, int start, int count, int after) {
}
public void onTextChanged(CharSequence s, int start, int before, int count) {
saveDraft(addComment.getText().toString(), "new", draftIdOnCreate);
draftSaved.setVisibility(View.VISIBLE);
}
});
if(!connToInternet) {
disableProcessButton();
} else {
}
else {
replyButton.setOnClickListener(replyToIssue);
@ -123,6 +200,41 @@ public class ReplyToIssueActivity extends BaseActivity {
}
private void saveDraft(String draftText, String commentId, long draftIdOnCreate) {
TinyDB tinyDb = new TinyDB(getApplicationContext());
int repositoryId = (int) tinyDb.getLong("repositoryId", 0);
int currentActiveAccountId = tinyDb.getInt("currentActiveAccountId");
int issueNumber = Integer.parseInt(tinyDb.getString("issueNumber"));
DraftsApi draftsApi = new DraftsApi(appCtx);
if(draftIdOnCreate == 0) {
draftsApi.insertDraft(repositoryId, currentActiveAccountId, issueNumber, draftText, StaticGlobalVariables.draftTypeComment, commentId);
}
else {
DraftsApi.updateDraft(draftText, (int) draftIdOnCreate, commentId); //updateDraftByIssueIdAsyncTask(draftText, issueNumber, repositoryId, commentId);
}
}
private long returnDraftId(String draftText) {
TinyDB tinyDb = new TinyDB(getApplicationContext());
int repositoryId = (int) tinyDb.getLong("repositoryId", 0);
int currentActiveAccountId = tinyDb.getInt("currentActiveAccountId");
int issueNumber = Integer.parseInt(tinyDb.getString("issueNumber"));
DraftsApi draftsApi = new DraftsApi(appCtx);
return draftsApi.insertDraft(repositoryId, currentActiveAccountId, issueNumber, draftText, StaticGlobalVariables.draftTypeComment, "");
}
public void loadCollaboratorsList() {
final TinyDB tinyDb = new TinyDB(appCtx);
@ -153,13 +265,13 @@ public class ReplyToIssueActivity extends BaseActivity {
if(!response.body().get(i).getFull_name().equals("")) {
fullName = response.body().get(i).getFull_name();
}
defaultMentionAdapter.add(
new Mention(response.body().get(i).getUsername(), fullName, response.body().get(i).getAvatar_url()));
defaultMentionAdapter.add(new Mention(response.body().get(i).getUsername(), fullName, response.body().get(i).getAvatar_url()));
}
} else {
}
else {
Log.i("onResponse", String.valueOf(response.code()));
Log.i(TAG, String.valueOf(response.code()));
}
@ -167,42 +279,35 @@ public class ReplyToIssueActivity extends BaseActivity {
@Override
public void onFailure(@NonNull Call<List<Collaborators>> call, @NonNull Throwable t) {
Log.i("onFailure", t.getMessage());
Log.e(TAG, t.toString());
}
});
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
onClickListener = view -> finish();
}
private View.OnClickListener replyToIssue = new View.OnClickListener() {
public void onClick(View v) {
processNewCommentReply();
}
};
private View.OnClickListener replyToIssue = v -> processNewCommentReply();
private void processNewCommentReply() {
String newReplyDT = addComment.getText().toString();
boolean connToInternet = AppUtil.haveNetworkConnection(appCtx);
boolean connToInternet = AppUtil.hasNetworkConnection(appCtx);
if(!connToInternet) {
Toasty.info(ctx, getResources().getString(R.string.checkNetConnection));
Toasty.error(ctx, getResources().getString(R.string.checkNetConnection));
return;
}
if(newReplyDT.equals("")) {
Toasty.info(ctx, getString(R.string.commentEmptyError));
Toasty.error(ctx, getString(R.string.commentEmptyError));
}
else {
@ -241,10 +346,18 @@ public class ReplyToIssueActivity extends BaseActivity {
if(response.code() == 201) {
Toasty.info(ctx, getString(R.string.commentSuccess));
Toasty.success(ctx, getString(R.string.commentSuccess));
tinyDb.putBoolean("commentPosted", true);
tinyDb.putBoolean("resumeIssues", true);
tinyDb.putBoolean("resumePullRequests", true);
// delete draft comment
if(tinyDb.getBoolean("draftsCommentsDeletionEnabled")) {
DraftsApi draftsApi = new DraftsApi(appCtx);
draftsApi.deleteSingleDraft((int) draftIdOnCreate);
}
finish();
}
@ -260,7 +373,7 @@ public class ReplyToIssueActivity extends BaseActivity {
else {
enableProcessButton();
Toasty.info(ctx, getString(R.string.commentError));
Toasty.error(ctx, getString(R.string.commentError));
}
@ -268,31 +381,51 @@ public class ReplyToIssueActivity extends BaseActivity {
@Override
public void onFailure(@NonNull Call<Issues> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
Log.e(TAG, t.toString());
enableProcessButton();
}
});
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.reply_to_issue, menu);
return super.onCreateOptionsMenu(menu);
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
switch(item.getItemId()) {
case R.id.replyToIssueMenu:
Intent fragmentIntent = new Intent(ReplyToIssueActivity.this, MainActivity.class);
fragmentIntent.putExtra("launchFragment", "drafts");
ReplyToIssueActivity.this.startActivity(fragmentIntent);
break;
default:
return super.onOptionsItemSelected(item);
}
return true;
}
private void disableProcessButton() {
replyButton.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
replyButton.setBackground(shape);
}
private void enableProcessButton() {
replyButton.setEnabled(true);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.btnBackground));
replyButton.setBackground(shape);
}
}

View File

@ -1,7 +1,10 @@
package org.mian.gitnex.activities;
import android.annotation.SuppressLint;
import android.content.ClipData;
import android.content.ClipboardManager;
import android.content.Context;
import android.content.DialogInterface;
import android.content.Intent;
import android.content.res.ColorStateList;
import android.graphics.Typeface;
@ -16,6 +19,7 @@ import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AlertDialog;
import androidx.appcompat.widget.Toolbar;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentManager;
@ -29,7 +33,6 @@ import org.mian.gitnex.fragments.BottomSheetIssuesFilterFragment;
import org.mian.gitnex.fragments.BottomSheetMilestonesFilterFragment;
import org.mian.gitnex.fragments.BottomSheetPullRequestFilterFragment;
import org.mian.gitnex.fragments.BottomSheetRepoFragment;
import org.mian.gitnex.fragments.BranchesFragment;
import org.mian.gitnex.fragments.CollaboratorsFragment;
import org.mian.gitnex.fragments.FilesFragment;
import org.mian.gitnex.fragments.IssuesFragment;
@ -39,14 +42,18 @@ import org.mian.gitnex.fragments.PullRequestsFragment;
import org.mian.gitnex.fragments.ReleasesFragment;
import org.mian.gitnex.fragments.RepoInfoFragment;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.Branches;
import org.mian.gitnex.models.UserRepositories;
import org.mian.gitnex.models.WatchInfo;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
/**
* Author M M Arif
@ -62,60 +69,22 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
private FragmentRefreshListener fragmentRefreshListener;
private FragmentRefreshListenerPr fragmentRefreshListenerPr;
private FragmentRefreshListenerMilestone fragmentRefreshListenerMilestone;
private FragmentRefreshListenerFiles fragmentRefreshListenerFiles;
final Context ctx = this;
private final Context ctx = this;
private Context appCtx;
// issues interface
public FragmentRefreshListener getFragmentRefreshListener() {
private TinyDB tinyDB;
return fragmentRefreshListener;
}
private String instanceUrl;
private String loginUid;
private String instanceToken;
public void setFragmentRefreshListener(FragmentRefreshListener fragmentRefreshListener) {
private String repositoryOwner;
private String repositoryName;
this.fragmentRefreshListener = fragmentRefreshListener;
}
public interface FragmentRefreshListener {
void onRefresh(String text);
}
// pr interface
public FragmentRefreshListenerPr getFragmentRefreshListenerPr() {
return fragmentRefreshListenerPr;
}
public void setFragmentRefreshListenerPr(FragmentRefreshListenerPr fragmentRefreshListenerPr) {
this.fragmentRefreshListenerPr = fragmentRefreshListenerPr;
}
public interface FragmentRefreshListenerPr {
void onRefresh(String text);
}
// milestones interface
public FragmentRefreshListenerMilestone getFragmentRefreshListenerMilestone() {
return fragmentRefreshListenerMilestone;
}
public void setFragmentRefreshListenerMilestone(FragmentRefreshListenerMilestone fragmentRefreshListenerMilestone) {
this.fragmentRefreshListenerMilestone = fragmentRefreshListenerMilestone;
}
public interface FragmentRefreshListenerMilestone {
void onRefresh(String text);
}
public static ViewPager mViewPager;
private int tabsCount;
@Override
protected int getLayoutResourceId() {
@ -129,40 +98,32 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
TinyDB tinyDb = new TinyDB(appCtx);
String repoFullName = tinyDb.getString("repoFullName");
String[] parts = repoFullName.split("/");
String repoName1 = parts[1];
tinyDB = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
final String repoOwner = parts[0];
final String loginUid = tinyDb.getString("loginUid");
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
tinyDb.putString("repoIssuesState", "open");
tinyDb.putString("repoPrState", "open");
tinyDb.putString("milestoneState", "open");
String appLocale = tinyDb.getString("locale");
AppUtil.setAppLocale(getResources(), appLocale);
String[] repoNameParts = tinyDB.getString("repoFullName").split("/");
repositoryOwner = repoNameParts[0];
repositoryName = repoNameParts[1];
Toolbar toolbar = findViewById(R.id.toolbar);
TextView toolbarTitle = toolbar.findViewById(R.id.toolbar_title);
toolbarTitle.setText(repositoryName);
setSupportActionBar(toolbar);
Objects.requireNonNull(getSupportActionBar()).setTitle(repoName1);
Objects.requireNonNull(getSupportActionBar()).setTitle(repositoryName);
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
SectionsPagerAdapter mSectionsPagerAdapter = new SectionsPagerAdapter(getSupportFragmentManager());
instanceUrl = tinyDB.getString("instanceUrl");
loginUid = tinyDB.getString("loginUid");
instanceToken = "token " + tinyDB.getString(loginUid + "-token");
ViewPager mViewPager = findViewById(R.id.container);
mViewPager.setAdapter(mSectionsPagerAdapter);
TabLayout tabLayout = findViewById(R.id.tabs);
tinyDB.putString("repoIssuesState", "open");
tinyDB.putString("repoPrState", "open");
tinyDB.putString("milestoneState", "open");
Typeface myTypeface;
switch(tinyDb.getInt("customFontId", -1)) {
switch(tinyDB.getInt("customFontId", -1)) {
case 0:
myTypeface = Typeface.createFromAsset(ctx.getAssets(), "fonts/roboto.ttf");
@ -179,34 +140,50 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
}
toolbarTitle.setTypeface(myTypeface);
toolbarTitle.setText(repoName1);
ViewGroup vg = (ViewGroup) tabLayout.getChildAt(0);
int tabsCount = vg.getChildCount();
TabLayout tabLayout = findViewById(R.id.tabs);
ViewGroup viewGroup = (ViewGroup) tabLayout.getChildAt(0);
tabsCount = viewGroup.getChildCount();
for(int j = 0; j < tabsCount; j++) {
ViewGroup vgTab = (ViewGroup) vg.getChildAt(j);
ViewGroup vgTab = (ViewGroup) viewGroup.getChildAt(j);
int tabChildCount = vgTab.getChildCount();
for(int i = 0; i < tabChildCount; i++) {
View tabViewChild = vgTab.getChildAt(i);
if(tabViewChild instanceof TextView) {
((TextView) tabViewChild).setTypeface(myTypeface);
}
}
}
// only show Collaborators if you have permission to
final View collaboratorTab = vg.getChildAt(8);
if(tinyDb.getBoolean("isRepoAdmin")) {
// Only show collaborators tab, if you have permission to
View collaboratorTab = viewGroup.getChildAt(7);
if(tinyDB.getBoolean("isRepoAdmin") || new Version(tinyDB.getString("giteaVersion")).higherOrEqual("1.12.0")) {
collaboratorTab.setVisibility(View.VISIBLE);
}
else {
tabsCount--;
collaboratorTab.setVisibility(View.GONE);
}
mViewPager = findViewById(R.id.container);
mViewPager.addOnPageChangeListener(new TabLayout.TabLayoutOnPageChangeListener(tabLayout));
tabLayout.addOnTabSelectedListener(new TabLayout.ViewPagerOnTabSelectedListener(mViewPager));
if(tinyDb.getBoolean("enableCounterBadges")) {
SectionsPagerAdapter mSectionsPagerAdapter = new SectionsPagerAdapter(getSupportFragmentManager());
mViewPager.setAdapter(mSectionsPagerAdapter);
if(tinyDB.getBoolean("enableCounterBadges")) {
@SuppressLint("InflateParams") View tabHeader2 = LayoutInflater.from(this).inflate(R.layout.badge_issue, null);
textViewBadgeIssue = tabHeader2.findViewById(R.id.counterBadgeIssue);
@ -221,41 +198,48 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
textViewBadgePull.setVisibility(View.GONE);
textViewBadgeRelease.setVisibility(View.GONE);
getRepoInfo(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName1);
getRepoInfo(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repositoryOwner, repositoryName);
ColorStateList textColor = tabLayout.getTabTextColors();
// issue count
// Issue count
if(textViewBadgeIssue.getText() != "") {
TabLayout.Tab tabOpenIssues = tabLayout.getTabAt(2);
Objects.requireNonNull(tabLayout.getTabAt(2)).setCustomView(tabHeader2);
assert tabOpenIssues != null;
assert tabOpenIssues != null; // FIXME This should be cleaned up
TextView openIssueTabView = Objects.requireNonNull(tabOpenIssues.getCustomView()).findViewById(R.id.counterBadgeIssueText);
openIssueTabView.setTextColor(textColor);
}
// pull count
// Pull request count
if(textViewBadgePull.getText() != "") { // only show if API returned a number
Objects.requireNonNull(tabLayout.getTabAt(3)).setCustomView(tabHeader4);
TabLayout.Tab tabOpenPulls = tabLayout.getTabAt(3);
assert tabOpenPulls != null;
assert tabOpenPulls != null; // FIXME This should be cleaned up
TextView openPullTabView = Objects.requireNonNull(tabOpenPulls.getCustomView()).findViewById(R.id.counterBadgePullText);
openPullTabView.setTextColor(textColor);
}
// release count
if(new Version("1.11.4").less(tinyDb.getString("giteaVersion"))) {
// Release count
if(new Version("1.11.4").less(tinyDB.getString("giteaVersion"))) {
if(textViewBadgeRelease.getText() != "") { // only show if API returned a number
Objects.requireNonNull(tabLayout.getTabAt(5)).setCustomView(tabHeader6);
TabLayout.Tab tabOpenRelease = tabLayout.getTabAt(5);
assert tabOpenRelease != null;
Objects.requireNonNull(tabLayout.getTabAt(4)).setCustomView(tabHeader6);
TabLayout.Tab tabOpenRelease = tabLayout.getTabAt(4);
assert tabOpenRelease != null; // FIXME This should be cleaned up
TextView openReleaseTabView = Objects.requireNonNull(tabOpenRelease.getCustomView()).findViewById(R.id.counterBadgeReleaseText);
openReleaseTabView.setTextColor(textColor);
}
}
}
checkRepositoryStarStatus(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName1);
checkRepositoryWatchStatus(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName1);
checkRepositoryStarStatus(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repositoryOwner, repositoryName);
checkRepositoryWatchStatus(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repositoryOwner, repositoryName);
}
@ -263,17 +247,10 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
public void onResume() {
super.onResume();
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
final String loginUid = tinyDb.getString("loginUid");
String repoFullName = tinyDb.getString("repoFullName");
String[] parts = repoFullName.split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
if(tinyDb.getBoolean("enableCounterIssueBadge")) {
getRepoInfo(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName);
if(tinyDB.getBoolean("enableCounterIssueBadge")) {
getRepoInfo(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repositoryOwner, repositoryName);
}
}
@ -293,27 +270,44 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
int id = item.getItemId();
switch(id) {
case android.R.id.home:
finish();
return true;
case R.id.repoMenu:
BottomSheetRepoFragment bottomSheet = new BottomSheetRepoFragment();
bottomSheet.show(getSupportFragmentManager(), "repoBottomSheet");
return true;
case R.id.filter:
BottomSheetIssuesFilterFragment filterBottomSheet = new BottomSheetIssuesFilterFragment();
filterBottomSheet.show(getSupportFragmentManager(), "repoFilterMenuBottomSheet");
return true;
case R.id.filterPr:
BottomSheetPullRequestFilterFragment filterPrBottomSheet = new BottomSheetPullRequestFilterFragment();
filterPrBottomSheet.show(getSupportFragmentManager(), "repoFilterMenuPrBottomSheet");
return true;
case R.id.filterMilestone:
BottomSheetMilestonesFilterFragment filterMilestoneBottomSheet = new BottomSheetMilestonesFilterFragment();
filterMilestoneBottomSheet.show(getSupportFragmentManager(), "repoFilterMenuMilestoneBottomSheet");
return true;
case R.id.switchBranches:
chooseBranch();
return true;
case R.id.branchCommits:
Intent intent = new Intent(ctx, CommitsActivity.class);
intent.putExtra("branchName", tinyDB.getString("repoBranch"));
ctx.startActivity(intent);
return true;
default:
return super.onOptionsItemSelected(item);
}
}
@ -321,72 +315,165 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
@Override
public void onButtonClicked(String text) {
TinyDB tinyDb = new TinyDB(appCtx);
switch(text) {
case "label":
startActivity(new Intent(RepoDetailActivity.this, CreateLabelActivity.class));
break;
case "newIssue":
startActivity(new Intent(RepoDetailActivity.this, CreateIssueActivity.class));
break;
case "newMilestone":
startActivity(new Intent(RepoDetailActivity.this, CreateMilestoneActivity.class));
break;
case "addCollaborator":
startActivity(new Intent(RepoDetailActivity.this, AddCollaboratorToRepositoryActivity.class));
break;
case "chooseBranch":
chooseBranch();
break;
case "createRelease":
startActivity(new Intent(RepoDetailActivity.this, CreateReleaseActivity.class));
break;
case "openWebRepo":
Intent i = new Intent(Intent.ACTION_VIEW, Uri.parse(tinyDb.getString("repoHtmlUrl")));
Intent i = new Intent(Intent.ACTION_VIEW, Uri.parse(tinyDB.getString("repoHtmlUrl")));
startActivity(i);
break;
case "shareRepo":
Intent sharingIntent = new Intent(android.content.Intent.ACTION_SEND);
sharingIntent.setType("text/plain");
sharingIntent.putExtra(android.content.Intent.EXTRA_SUBJECT, tinyDb.getString("repoHtmlUrl"));
sharingIntent.putExtra(android.content.Intent.EXTRA_TEXT, tinyDb.getString("repoHtmlUrl"));
startActivity(Intent.createChooser(sharingIntent, tinyDb.getString("repoHtmlUrl")));
sharingIntent.putExtra(android.content.Intent.EXTRA_SUBJECT, tinyDB.getString("repoHtmlUrl"));
sharingIntent.putExtra(android.content.Intent.EXTRA_TEXT, tinyDB.getString("repoHtmlUrl"));
startActivity(Intent.createChooser(sharingIntent, tinyDB.getString("repoHtmlUrl")));
break;
case "copyRepoUrl":
ClipboardManager clipboard = (ClipboardManager) Objects.requireNonNull(ctx).getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText("repoUrl", tinyDB.getString("repoHtmlUrl"));
assert clipboard != null;
clipboard.setPrimaryClip(clip);
Toasty.info(ctx, ctx.getString(R.string.copyIssueUrlToastMsg));
break;
case "newFile":
startActivity(new Intent(RepoDetailActivity.this, CreateFileActivity.class));
break;
case "openIssues":
if(getFragmentRefreshListener() != null) {
getFragmentRefreshListener().onRefresh("open");
}
break;
case "closedIssues":
if(getFragmentRefreshListener() != null) {
getFragmentRefreshListener().onRefresh("closed");
}
break;
case "openPr":
if(getFragmentRefreshListenerPr() != null) {
getFragmentRefreshListenerPr().onRefresh("open");
}
break;
case "closedPr":
if(getFragmentRefreshListenerPr() != null) {
getFragmentRefreshListenerPr().onRefresh("closed");
}
break;
case "openMilestone":
if(getFragmentRefreshListenerMilestone() != null) {
getFragmentRefreshListenerMilestone().onRefresh("open");
}
break;
case "closedMilestone":
if(getFragmentRefreshListenerMilestone() != null) {
getFragmentRefreshListenerMilestone().onRefresh("closed");
}
break;
case "repoSettings":
startActivity(new Intent(RepoDetailActivity.this, RepositorySettingsActivity.class));
break;
case "newPullRequest":
startActivity(new Intent(RepoDetailActivity.this, CreatePullRequestActivity.class));
break;
}
}
private void chooseBranch() {
Call<List<Branches>> call = RetrofitClient.getInstance(instanceUrl, ctx)
.getApiInterface()
.getBranches(instanceToken, repositoryOwner, repositoryName);
call.enqueue(new Callback<List<Branches>>() {
@Override
public void onResponse(@NonNull Call<List<Branches>> call, @NonNull Response<List<Branches>> response) {
if(response.code() == 200) {
List<String> branchesList = new ArrayList<>();
int selectedBranch = 0;
assert response.body() != null;
for(int i = 0; i < response.body().size(); i++) {
Branches branches = response.body().get(i);
branchesList.add(branches.getName());
if(tinyDB.getString("repoBranch").equals(branches.getName())) {
selectedBranch = i;
}
}
AlertDialog.Builder pBuilder = new AlertDialog.Builder(ctx);
pBuilder.setTitle(R.string.pageTitleChooseBranch);
pBuilder.setSingleChoiceItems(branchesList.toArray(new String[0]), selectedBranch, new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface dialogInterface, int i) {
tinyDB.putString("repoBranch", branchesList.get(i));
if(getFragmentRefreshListenerFiles() != null) {
getFragmentRefreshListenerFiles().onRefresh(branchesList.get(i));
}
dialogInterface.dismiss();
}
});
pBuilder.setNeutralButton(R.string.cancelButton, null);
pBuilder.create().show();
}
}
@Override
public void onFailure(@NonNull Call<List<Branches>> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
}
});
}
public class SectionsPagerAdapter extends FragmentStatePagerAdapter {
SectionsPagerAdapter(FragmentManager fm) {
@ -398,54 +485,55 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
@Override
public Fragment getItem(int position) {
TinyDB tinyDb = new TinyDB(appCtx);
String repoFullName = tinyDb.getString("repoFullName");
String[] parts = repoFullName.split("/");
String repoOwner = parts[0];
String repoName = parts[1];
Fragment fragment = null;
switch(position) {
case 0: // information
return RepoInfoFragment.newInstance(repoOwner, repoName);
case 1: // files
return FilesFragment.newInstance(repoOwner, repoName);
case 2: // issues
case 0: // Repository details
return RepoInfoFragment.newInstance(repositoryOwner, repositoryName);
case 1: // Files
return FilesFragment.newInstance(repositoryOwner, repositoryName, tinyDB.getString("repoBranch"));
case 2: // Issues
fragment = new IssuesFragment();
break;
case 3: // pull requests
case 3: // Pull requests
fragment = new PullRequestsFragment();
break;
case 4: // branches
return BranchesFragment.newInstance(repoOwner, repoName);
case 5: // releases
return ReleasesFragment.newInstance(repoOwner, repoName);
case 6: // milestones
case 4: // Releases
return ReleasesFragment.newInstance(repositoryOwner, repositoryName);
case 5: // Milestones
fragment = new MilestonesFragment();
break;
case 7: // labels
return LabelsFragment.newInstance(repoOwner, repoName);
case 8: // collaborators
return CollaboratorsFragment.newInstance(repoOwner, repoName);
case 6: // Labels
return LabelsFragment.newInstance(repositoryOwner, repositoryName);
case 7: // Collaborators
return CollaboratorsFragment.newInstance(repositoryOwner, repositoryName);
}
assert fragment != null;
return fragment;
}
@Override
public int getCount() {
return 9;
return tabsCount;
}
}
private void getRepoInfo(String instanceUrl, String token, final String owner, String repo) {
TinyDB tinyDb = new TinyDB(appCtx);
Call<UserRepositories> call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().getUserRepository(token, owner, repo);
call.enqueue(new Callback<UserRepositories>() {
@Override
@ -453,33 +541,33 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
UserRepositories repoInfo = response.body();
if(response.isSuccessful()) {
if(response.code() == 200) {
if(tinyDb.getBoolean("enableCounterBadges")) {
if(tinyDB.getBoolean("enableCounterBadges")) {
assert repoInfo != null;
if(repoInfo.getOpen_issues_count() != null) {
textViewBadgeIssue.setVisibility(View.VISIBLE);
textViewBadgeIssue.setText(repoInfo.getOpen_issues_count());
}
if(repoInfo.getOpen_pull_count() != null) {
textViewBadgePull.setVisibility(View.VISIBLE);
textViewBadgePull.setText(repoInfo.getOpen_pull_count());
}
if(repoInfo.getRelease_count() != null) {
textViewBadgeRelease.setVisibility(View.VISIBLE);
textViewBadgeRelease.setText(repoInfo.getRelease_count());
}
}
}
}
else {
Log.e("onFailure", String.valueOf(response.code()));
}
@ -497,17 +585,13 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
private void checkRepositoryStarStatus(String instanceUrl, String instanceToken, final String owner, String repo) {
Call<JsonElement> call;
call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().checkRepoStarStatus(instanceToken, owner, repo);
Call<JsonElement> call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().checkRepoStarStatus(instanceToken, owner, repo);
call.enqueue(new Callback<JsonElement>() {
@Override
public void onResponse(@NonNull Call<JsonElement> call, @NonNull retrofit2.Response<JsonElement> response) {
TinyDB tinyDb = new TinyDB(appCtx);
tinyDb.putInt("repositoryStarStatus", response.code());
tinyDB.putInt("repositoryStarStatus", response.code());
}
@ -525,22 +609,23 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
Call<WatchInfo> call;
call = RetrofitClient.getInstance(instanceUrl, ctx).getApiInterface().checkRepoWatchStatus(instanceToken, owner, repo);
call.enqueue(new Callback<WatchInfo>() {
@Override
public void onResponse(@NonNull Call<WatchInfo> call, @NonNull retrofit2.Response<WatchInfo> response) {
TinyDB tinyDb = new TinyDB(appCtx);
if(response.code() == 200) {
assert response.body() != null;
if(response.body().getSubscribed()) {
tinyDb.putBoolean("repositoryWatchStatus", true);
tinyDB.putBoolean("repositoryWatchStatus", true);
}
}
else {
tinyDb.putBoolean("repositoryWatchStatus", false);
tinyDB.putBoolean("repositoryWatchStatus", false);
}
}
@ -554,4 +639,32 @@ public class RepoDetailActivity extends BaseActivity implements BottomSheetRepoF
}
// Issues interface
public FragmentRefreshListener getFragmentRefreshListener() { return fragmentRefreshListener; }
public void setFragmentRefreshListener(FragmentRefreshListener fragmentRefreshListener) { this.fragmentRefreshListener = fragmentRefreshListener; }
public interface FragmentRefreshListener { void onRefresh(String text); }
// Pull request interface
public FragmentRefreshListenerPr getFragmentRefreshListenerPr() { return fragmentRefreshListenerPr; }
public void setFragmentRefreshListenerPr(FragmentRefreshListenerPr fragmentRefreshListenerPr) { this.fragmentRefreshListenerPr = fragmentRefreshListenerPr; }
public interface FragmentRefreshListenerPr { void onRefresh(String text); }
// Milestones interface
public FragmentRefreshListenerMilestone getFragmentRefreshListenerMilestone() { return fragmentRefreshListenerMilestone; }
public void setFragmentRefreshListenerMilestone(FragmentRefreshListenerMilestone fragmentRefreshListenerMilestone) { this.fragmentRefreshListenerMilestone = fragmentRefreshListenerMilestone; }
public interface FragmentRefreshListenerMilestone { void onRefresh(String text); }
// Files interface
public FragmentRefreshListenerFiles getFragmentRefreshListenerFiles() { return fragmentRefreshListenerFiles; }
public void setFragmentRefreshListenerFiles(FragmentRefreshListenerFiles fragmentRefreshListenerFiles) { this.fragmentRefreshListenerFiles = fragmentRefreshListenerFiles; }
public interface FragmentRefreshListenerFiles { void onRefresh(String text); }
}

View File

@ -0,0 +1,296 @@
package org.mian.gitnex.activities;
import android.annotation.SuppressLint;
import android.content.Context;
import android.os.Bundle;
import android.os.Handler;
import android.text.method.ScrollingMovementMethod;
import android.util.Log;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.inputmethod.EditorInfo;
import android.widget.ImageView;
import android.widget.ProgressBar;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.widget.SearchView;
import androidx.appcompat.widget.Toolbar;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.RepoForksAdapter;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.StaticGlobalVariables;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.UserRepositories;
import java.util.ArrayList;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
/**
* Author M M Arif
*/
public class RepoForksActivity extends BaseActivity {
final Context ctx = this;
private Context appCtx;
private View.OnClickListener onClickListener;
private TextView noData;
private ProgressBar progressBar;
private String TAG = "RepositoryForks";
private int resultLimit = StaticGlobalVariables.resultLimitOldGiteaInstances;
private int pageSize = 1;
private RecyclerView recyclerView;
private List<UserRepositories> forksList;
private RepoForksAdapter adapter;
private ProgressBar progressLoadMore;
@Override
protected int getLayoutResourceId() {
return R.layout.activity_forks;
}
@SuppressLint("DefaultLocale")
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
Toolbar toolbar = findViewById(R.id.toolbar);
setSupportActionBar(toolbar);
TinyDB tinyDb = new TinyDB(appCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
final String loginUid = tinyDb.getString("loginUid");
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
String repoFullNameForForks = getIntent().getStringExtra("repoFullNameForForks");
assert repoFullNameForForks != null;
String[] parts = repoFullNameForForks.split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
TextView toolbar_title = findViewById(R.id.toolbar_title);
toolbar_title.setMovementMethod(new ScrollingMovementMethod());
toolbar_title.setText(String.format("%s : %s", ctx.getResources().getString(R.string.infoTabRepoForksCount), repoName));
ImageView closeActivity = findViewById(R.id.close);
noData = findViewById(R.id.noData);
progressLoadMore = findViewById(R.id.progressLoadMore);
progressBar = findViewById(R.id.progress_bar);
SwipeRefreshLayout swipeRefresh = findViewById(R.id.pullToRefresh);
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
// if gitea is 1.12 or higher use the new limit (resultLimitNewGiteaInstances)
if(new Version(tinyDb.getString("giteaVersion")).higherOrEqual("1.12")) {
resultLimit = StaticGlobalVariables.resultLimitNewGiteaInstances;
}
recyclerView = findViewById(R.id.recyclerView);
forksList = new ArrayList<>();
DividerItemDecoration dividerItemDecoration = new DividerItemDecoration(recyclerView.getContext(),
DividerItemDecoration.VERTICAL);
recyclerView.addItemDecoration(dividerItemDecoration);
swipeRefresh.setOnRefreshListener(() -> new Handler().postDelayed(() -> {
swipeRefresh.setRefreshing(false);
loadInitial(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, pageSize, resultLimit);
adapter.notifyDataChanged();
}, 200));
adapter = new RepoForksAdapter(ctx, forksList);
adapter.setLoadMoreListener(() -> recyclerView.post(() -> {
if(forksList.size() == resultLimit || pageSize == resultLimit) {
int page = (forksList.size() + resultLimit) / resultLimit;
loadMore(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, page, resultLimit);
}
}));
recyclerView.setHasFixedSize(true);
recyclerView.setLayoutManager(new LinearLayoutManager(ctx));
recyclerView.setAdapter(adapter);
loadInitial(instanceUrl, Authorization.returnAuthentication(ctx, loginUid, instanceToken), repoOwner, repoName, pageSize, resultLimit);
}
private void loadInitial(String instanceUrl, String instanceToken, String repoOwner, String repoName, int pageSize, int resultLimit) {
Call<List<UserRepositories>> call = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.getRepositoryForks(instanceToken, repoOwner, repoName, pageSize, resultLimit);
call.enqueue(new Callback<List<UserRepositories>>() {
@Override
public void onResponse(@NonNull Call<List<UserRepositories>> call, @NonNull Response<List<UserRepositories>> response) {
if(response.isSuccessful()) {
assert response.body() != null;
if(response.body().size() > 0) {
forksList.clear();
forksList.addAll(response.body());
adapter.notifyDataChanged();
noData.setVisibility(View.GONE);
}
else {
forksList.clear();
adapter.notifyDataChanged();
noData.setVisibility(View.VISIBLE);
}
progressBar.setVisibility(View.GONE);
}
else {
Log.e(TAG, String.valueOf(response.code()));
}
}
@Override
public void onFailure(@NonNull Call<List<UserRepositories>> call, @NonNull Throwable t) {
Log.e(TAG, t.toString());
}
});
}
private void loadMore(String instanceUrl, String instanceToken, String repoOwner, String repoName, int page, int resultLimit) {
progressLoadMore.setVisibility(View.VISIBLE);
Call<List<UserRepositories>> call = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.getRepositoryForks(instanceToken, repoOwner, repoName, page, resultLimit);
call.enqueue(new Callback<List<UserRepositories>>() {
@Override
public void onResponse(@NonNull Call<List<UserRepositories>> call, @NonNull Response<List<UserRepositories>> response) {
if(response.isSuccessful()) {
//remove loading view
forksList.remove(forksList.size() - 1);
List<UserRepositories> result = response.body();
assert result != null;
if(result.size() > 0) {
pageSize = result.size();
forksList.addAll(result);
}
else {
adapter.setMoreDataAvailable(false);
}
adapter.notifyDataChanged();
progressLoadMore.setVisibility(View.GONE);
}
else {
Log.e(TAG, String.valueOf(response.code()));
}
}
@Override
public void onFailure(@NonNull Call<List<UserRepositories>> call, @NonNull Throwable t) {
Log.e(TAG, t.toString());
}
});
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.search_menu, menu);
MenuItem searchItem = menu.findItem(R.id.action_search);
SearchView searchView = (SearchView) searchItem.getActionView();
searchView.setImeOptions(EditorInfo.IME_ACTION_DONE);
searchView.setOnQueryTextListener(new androidx.appcompat.widget.SearchView.OnQueryTextListener() {
@Override
public boolean onQueryTextSubmit(String query) {
return false;
}
@Override
public boolean onQueryTextChange(String newText) {
filter(newText);
return true;
}
});
return super.onCreateOptionsMenu(menu);
}
private void filter(String text) {
List<UserRepositories> arr = new ArrayList<>();
for(UserRepositories d : forksList) {
if(d.getName().toLowerCase().contains(text) || d.getDescription().toLowerCase().contains(text)) {
arr.add(d);
}
}
adapter.updateList(arr);
}
private void initCloseListener() {
onClickListener = view -> {
getIntent().removeExtra("repoFullNameForForks");
finish();
};
}
}

View File

@ -2,19 +2,19 @@ package org.mian.gitnex.activities;
import android.content.Context;
import android.os.Bundle;
import androidx.annotation.Nullable;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProvider;
import android.view.View;
import android.widget.GridView;
import android.widget.ImageView;
import android.widget.ProgressBar;
import android.widget.TextView;
import androidx.annotation.Nullable;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProvider;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.RepoStargazersAdapter;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.viewmodels.RepoStargazersViewModel;
import java.util.List;
@ -93,12 +93,8 @@ public class RepoStargazersActivity extends BaseActivity {
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
onClickListener = view -> finish();
}
}

View File

@ -2,19 +2,19 @@ package org.mian.gitnex.activities;
import android.content.Context;
import android.os.Bundle;
import androidx.annotation.Nullable;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProvider;
import android.view.View;
import android.widget.GridView;
import android.widget.ImageView;
import android.widget.ProgressBar;
import android.widget.TextView;
import androidx.annotation.Nullable;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProvider;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.RepoWatchersAdapter;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.viewmodels.RepoWatchersViewModel;
import java.util.List;
@ -93,12 +93,8 @@ public class RepoWatchersActivity extends BaseActivity {
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
onClickListener = view -> finish();
}
}

View File

@ -0,0 +1,435 @@
package org.mian.gitnex.activities;
import android.app.Dialog;
import android.content.Context;
import android.content.Intent;
import android.graphics.Color;
import android.graphics.drawable.ColorDrawable;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.ImageView;
import androidx.annotation.NonNull;
import com.google.gson.JsonElement;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.RepositoriesApi;
import org.mian.gitnex.databinding.ActivityRepositorySettingsBinding;
import org.mian.gitnex.databinding.CustomRepositoryDeleteDialogBinding;
import org.mian.gitnex.databinding.CustomRepositoryEditPropertiesDialogBinding;
import org.mian.gitnex.databinding.CustomRepositoryTransferDialogBinding;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.models.RepositoryTransfer;
import org.mian.gitnex.models.UserRepositories;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
*/
public class RepositorySettingsActivity extends BaseActivity {
private ActivityRepositorySettingsBinding viewBinding;
private CustomRepositoryEditPropertiesDialogBinding propBinding;
private CustomRepositoryDeleteDialogBinding deleteRepoBinding;
private CustomRepositoryTransferDialogBinding transferRepoBinding;
private Dialog dialogProp;
private Dialog dialogDeleteRepository;
private Dialog dialogTransferRepository;
private View.OnClickListener onClickListener;
private Context ctx = this;
private Context appCtx;
private TinyDB tinyDb;
private String instanceUrl;
private String loginUid;
private String instanceToken;
private String repositoryOwner;
private String repositoryName;
@Override
protected int getLayoutResourceId(){
return R.layout.activity_repository_settings;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
tinyDb = new TinyDB(appCtx);
viewBinding = ActivityRepositorySettingsBinding.inflate(getLayoutInflater());
View view = viewBinding.getRoot();
setContentView(view);
instanceUrl = tinyDb.getString("instanceUrl");
loginUid = tinyDb.getString("loginUid");
String repoFullName = tinyDb.getString("repoFullName");
String[] parts = repoFullName.split("/");
repositoryOwner = parts[0];
repositoryName = parts[1];
instanceToken = "token " + tinyDb.getString(loginUid + "-token");
ImageView closeActivity = findViewById(R.id.close);
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
// require gitea 1.12 or higher
if(new Version(tinyDb.getString("giteaVersion")).higherOrEqual("1.12.0")) {
viewBinding.transferOwnerFrame.setVisibility(View.VISIBLE);
}
viewBinding.editProperties.setOnClickListener(editProperties -> {
showRepositoryProperties();
});
viewBinding.deleteRepository.setOnClickListener(deleteRepository -> {
showDeleteRepository();
});
viewBinding.transferOwnerFrame.setOnClickListener(transferRepositoryOwnership -> {
showTransferRepository();
});
}
private void showTransferRepository() {
dialogTransferRepository = new Dialog(ctx, R.style.ThemeOverlay_MaterialComponents_Dialog_Alert);
if (dialogTransferRepository.getWindow() != null) {
dialogTransferRepository.getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
}
transferRepoBinding = CustomRepositoryTransferDialogBinding.inflate(LayoutInflater.from(ctx));
View view = transferRepoBinding.getRoot();
dialogTransferRepository.setContentView(view);
transferRepoBinding.cancel.setOnClickListener(editProperties -> {
dialogTransferRepository.dismiss();
});
transferRepoBinding.transfer.setOnClickListener(deleteRepo -> {
String newOwner = String.valueOf(transferRepoBinding.ownerNameForTransfer.getText());
String repoName = String.valueOf(transferRepoBinding.repoNameForTransfer.getText());
if(!repositoryName.equals(repoName)) {
Toasty.error(ctx, getString(R.string.repoSettingsDeleteError));
}
else if(newOwner.matches("")) {
Toasty.error(ctx, getString(R.string.repoTransferOwnerError));
}
else {
transferRepository(newOwner);
}
});
dialogTransferRepository.show();
}
private void transferRepository(String newOwner) {
RepositoryTransfer repositoryTransfer = new RepositoryTransfer(newOwner);
Call<JsonElement> transferCall = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.transferRepository(instanceToken, repositoryOwner, repositoryName, repositoryTransfer);
transferCall.enqueue(new Callback<JsonElement>() {
@Override
public void onResponse(@NonNull Call<JsonElement> call, @NonNull retrofit2.Response<JsonElement> response) {
transferRepoBinding.transfer.setVisibility(View.GONE);
transferRepoBinding.processingRequest.setVisibility(View.VISIBLE);
if (response.code() == 202) {
dialogTransferRepository.dismiss();
Toasty.success(ctx, getString(R.string.repoTransferSuccess));
finish();
RepositoriesApi.deleteRepository((int) tinyDb.getLong("repositoryId", 0));
Intent intent = new Intent(RepositorySettingsActivity.this, MainActivity.class);
RepositorySettingsActivity.this.startActivity(intent);
}
else if (response.code() == 404) {
transferRepoBinding.transfer.setVisibility(View.VISIBLE);
transferRepoBinding.processingRequest.setVisibility(View.GONE);
Toasty.error(ctx, getString(R.string.repoTransferError));
}
else {
transferRepoBinding.transfer.setVisibility(View.VISIBLE);
transferRepoBinding.processingRequest.setVisibility(View.GONE);
Toasty.error(ctx, getString(R.string.genericError));
}
}
@Override
public void onFailure(@NonNull Call<JsonElement> call, @NonNull Throwable t) {
transferRepoBinding.transfer.setVisibility(View.VISIBLE);
transferRepoBinding.processingRequest.setVisibility(View.GONE);
Toasty.error(ctx, getString(R.string.genericServerResponseError));
}
});
}
private void showDeleteRepository() {
dialogDeleteRepository = new Dialog(ctx, R.style.ThemeOverlay_MaterialComponents_Dialog_Alert);
if (dialogDeleteRepository.getWindow() != null) {
dialogDeleteRepository.getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
}
deleteRepoBinding = CustomRepositoryDeleteDialogBinding.inflate(LayoutInflater.from(ctx));
View view = deleteRepoBinding.getRoot();
dialogDeleteRepository.setContentView(view);
deleteRepoBinding.cancel.setOnClickListener(editProperties -> {
dialogDeleteRepository.dismiss();
});
deleteRepoBinding.delete.setOnClickListener(deleteRepo -> {
if(!repositoryName.equals(String.valueOf(deleteRepoBinding.repoNameForDeletion.getText()))) {
Toasty.error(ctx, getString(R.string.repoSettingsDeleteError));
}
else {
deleteRepository();
}
});
dialogDeleteRepository.show();
}
private void deleteRepository() {
Call<JsonElement> deleteCall = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.deleteRepository(instanceToken, repositoryOwner, repositoryName);
deleteCall.enqueue(new Callback<JsonElement>() {
@Override
public void onResponse(@NonNull Call<JsonElement> call, @NonNull retrofit2.Response<JsonElement> response) {
deleteRepoBinding.delete.setVisibility(View.GONE);
deleteRepoBinding.processingRequest.setVisibility(View.VISIBLE);
if (response.code() == 204) {
dialogDeleteRepository.dismiss();
Toasty.success(ctx, getString(R.string.repoDeletionSuccess));
finish();
RepositoriesApi.deleteRepository((int) tinyDb.getLong("repositoryId", 0));
Intent intent = new Intent(RepositorySettingsActivity.this, MainActivity.class);
RepositorySettingsActivity.this.startActivity(intent);
}
else {
deleteRepoBinding.delete.setVisibility(View.VISIBLE);
deleteRepoBinding.processingRequest.setVisibility(View.GONE);
Toasty.error(ctx, getString(R.string.genericError));
}
}
@Override
public void onFailure(@NonNull Call<JsonElement> call, @NonNull Throwable t) {
deleteRepoBinding.delete.setVisibility(View.VISIBLE);
deleteRepoBinding.processingRequest.setVisibility(View.GONE);
Toasty.error(ctx, getString(R.string.genericServerResponseError));
}
});
}
private void showRepositoryProperties() {
dialogProp = new Dialog(ctx, R.style.ThemeOverlay_MaterialComponents_Dialog_Alert);
if (dialogProp.getWindow() != null) {
dialogProp.getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
}
propBinding = CustomRepositoryEditPropertiesDialogBinding.inflate(LayoutInflater.from(ctx));
View view = propBinding.getRoot();
dialogProp.setContentView(view);
propBinding.cancel.setOnClickListener(editProperties -> {
dialogProp.dismiss();
});
Call<UserRepositories> call = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.getUserRepository(instanceToken, repositoryOwner, repositoryName);
call.enqueue(new Callback<UserRepositories>() {
@Override
public void onResponse(@NonNull Call<UserRepositories> call, @NonNull retrofit2.Response<UserRepositories> response) {
UserRepositories repoInfo = response.body();
propBinding.progressBar.setVisibility(View.GONE);
propBinding.mainView.setVisibility(View.VISIBLE);
if (response.code() == 200) {
assert repoInfo != null;
propBinding.repoName.setText(repoInfo.getName());
propBinding.repoWebsite.setText(repoInfo.getWebsite());
propBinding.repoDescription.setText(repoInfo.getDescription());
propBinding.repoPrivate.setChecked(repoInfo.getPrivateFlag());
propBinding.repoAsTemplate.setChecked(repoInfo.isTemplate());
propBinding.repoEnableIssues.setChecked(repoInfo.getHas_issues());
propBinding.repoEnableIssues.setOnCheckedChangeListener((buttonView, isChecked) -> {
if (isChecked) {
propBinding.repoEnableTimer.setVisibility(View.VISIBLE);
}
else {
propBinding.repoEnableTimer.setVisibility(View.GONE);
}
});
if(repoInfo.getInternal_tracker() != null) {
propBinding.repoEnableTimer.setChecked(repoInfo.getInternal_tracker().isEnable_time_tracker());
}
else {
propBinding.repoEnableTimer.setVisibility(View.GONE);
}
propBinding.repoEnableWiki.setChecked(repoInfo.isHas_wiki());
propBinding.repoEnablePr.setChecked(repoInfo.isHas_pull_requests());
propBinding.repoEnableMerge.setChecked(repoInfo.isAllow_merge_commits());
propBinding.repoEnableRebase.setChecked(repoInfo.isAllow_rebase());
propBinding.repoEnableSquash.setChecked(repoInfo.isAllow_squash_merge());
propBinding.repoEnableForceMerge.setChecked(repoInfo.isAllow_rebase_explicit());
}
else {
Toasty.error(ctx, getString(R.string.genericError));
}
}
@Override
public void onFailure(@NonNull Call<UserRepositories> call, @NonNull Throwable t) {
Toasty.error(ctx, getString(R.string.genericServerResponseError));
}
});
propBinding.save.setOnClickListener(saveProperties -> saveRepositoryProperties(String.valueOf(propBinding.repoName.getText()),
String.valueOf(propBinding.repoWebsite.getText()),
String.valueOf(propBinding.repoDescription.getText()),
propBinding.repoPrivate.isChecked(), propBinding.repoAsTemplate.isChecked(),
propBinding.repoEnableIssues.isChecked(), propBinding.repoEnableWiki.isChecked(),
propBinding.repoEnablePr.isChecked(), propBinding.repoEnableTimer.isChecked(),
propBinding.repoEnableMerge.isChecked(), propBinding.repoEnableRebase.isChecked(),
propBinding.repoEnableSquash.isChecked(), propBinding.repoEnableForceMerge.isChecked()));
dialogProp.show();
}
private void saveRepositoryProperties(String repoName, String repoWebsite, String repoDescription,
boolean repoPrivate, boolean repoAsTemplate, boolean repoEnableIssues, boolean repoEnableWiki,
boolean repoEnablePr, boolean repoEnableTimer, boolean repoEnableMerge, boolean repoEnableRebase,
boolean repoEnableSquash, boolean repoEnableForceMerge) {
UserRepositories.internalTimeTrackerObject repoPropsTimeTracker = new UserRepositories.internalTimeTrackerObject(repoEnableTimer);
UserRepositories repoProps;
if(!repoEnableIssues) {
repoProps = new UserRepositories(repoName, repoWebsite, repoDescription, repoPrivate, repoAsTemplate, repoEnableIssues, repoEnableWiki, repoEnablePr, repoEnableMerge,
repoEnableRebase, repoEnableSquash, repoEnableForceMerge);
}
else {
repoProps = new UserRepositories(repoName, repoWebsite, repoDescription, repoPrivate, repoAsTemplate, repoEnableIssues, repoEnableWiki, repoEnablePr, repoPropsTimeTracker, repoEnableMerge,
repoEnableRebase, repoEnableSquash, repoEnableForceMerge);
}
Call<UserRepositories> propsCall = RetrofitClient
.getInstance(instanceUrl, ctx)
.getApiInterface()
.updateRepositoryProperties(instanceToken, repositoryOwner, repositoryName, repoProps);
propsCall.enqueue(new Callback<UserRepositories>() {
@Override
public void onResponse(@NonNull Call<UserRepositories> call, @NonNull retrofit2.Response<UserRepositories> response) {
propBinding.save.setVisibility(View.GONE);
propBinding.processingRequest.setVisibility(View.VISIBLE);
if (response.code() == 200) {
tinyDb.putBoolean("hasIssues", repoEnableIssues);
tinyDb.putBoolean("hasPullRequests", repoEnablePr);
dialogProp.dismiss();
Toasty.success(ctx, getString(R.string.repoPropertiesSaveSuccess));
if(!repositoryName.equals(repoName)) {
finish();
RepositoriesApi.updateRepositoryOwnerAndName(repositoryOwner, repoName, (int) tinyDb.getLong("repositoryId", 0));
Intent intent = new Intent(RepositorySettingsActivity.this, MainActivity.class);
RepositorySettingsActivity.this.startActivity(intent);
}
}
else {
propBinding.save.setVisibility(View.VISIBLE);
propBinding.processingRequest.setVisibility(View.GONE);
Toasty.error(ctx, getString(R.string.genericError));
}
}
@Override
public void onFailure(@NonNull Call<UserRepositories> call, @NonNull Throwable t) {
propBinding.save.setVisibility(View.VISIBLE);
propBinding.processingRequest.setVisibility(View.GONE);
Toasty.error(ctx, getString(R.string.genericServerResponseError));
}
});
}
private void initCloseListener() {
onClickListener = view -> finish();
}
}

View File

@ -9,8 +9,9 @@ import android.widget.Switch;
import android.widget.TextView;
import androidx.appcompat.app.AlertDialog;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.helpers.Version;
/**
* Author M M Arif
@ -27,13 +28,14 @@ public class SettingsAppearanceActivity extends BaseActivity {
private static String[] codeBlockList = {"Green - Black", "White - Black", "Grey - Black", "White - Grey", "Dark - White"};
private static int codeBlockSelectedChoice = 0;
private static String[] homeScreenList = {"My Repositories", "Starred Repositories", "Organizations", "Repositories", "Profile"};
private static String[] homeScreenList = {"My Repositories", "Starred Repositories", "Organizations", "Repositories", "Profile", "Explore", "Drafts"};
private static String[] homeScreenListNew = {"My Repositories", "Starred Repositories", "Organizations", "Repositories", "Profile", "Explore", "Drafts", "Notifications"};
private static int homeScreenSelectedChoice = 0;
private static String[] customFontList = {"Roboto", "Manrope", "Source Code Pro"};
private static int customFontSelectedChoice = 0;
private static String[] themeList = {"Dark", "Light", "Auto (Day/Night)"};
private static String[] themeList = {"Dark", "Light", "Auto (Light / Dark)", "Retro", "Auto (Retro / Dark)"};
private static int themeSelectedChoice = 0;
@Override
@ -69,6 +71,11 @@ public class SettingsAppearanceActivity extends BaseActivity {
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
if(new Version(tinyDb.getString("giteaVersion")).higherOrEqual("1.12.3")) {
homeScreenList = homeScreenListNew;
}
if(!tinyDb.getString("timeStr").isEmpty()) {
tvDateTimeSelected.setText(tinyDb.getString("timeStr"));
}
@ -121,11 +128,11 @@ public class SettingsAppearanceActivity extends BaseActivity {
if (isChecked) {
tinyDb.putBoolean("enableCounterBadges", true);
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
}
else {
tinyDb.putBoolean("enableCounterBadges", false);
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
}
});
@ -154,7 +161,7 @@ public class SettingsAppearanceActivity extends BaseActivity {
this.recreate();
this.overridePendingTransition(0, 0);
dialogInterfaceTheme.dismiss();
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
});
@ -187,7 +194,7 @@ public class SettingsAppearanceActivity extends BaseActivity {
this.recreate();
this.overridePendingTransition(0, 0);
dialogInterfaceCustomFont.dismiss();
Toasty.info(appCtx, appCtx.getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, appCtx.getResources().getString(R.string.settingsSave));
});
@ -201,7 +208,7 @@ public class SettingsAppearanceActivity extends BaseActivity {
AlertDialog.Builder hsBuilder = new AlertDialog.Builder(SettingsAppearanceActivity.this);
hsBuilder.setTitle(R.string.settingshomeScreenSelectorDialogTitle);
hsBuilder.setTitle(R.string.settingsHomeScreenSelectorDialogTitle);
if(homeScreenSelectedChoice != -1) {
hsBuilder.setCancelable(true);
}
@ -217,7 +224,7 @@ public class SettingsAppearanceActivity extends BaseActivity {
tinyDb.putInt("homeScreenId", i);
dialogInterfaceHomeScreen.dismiss();
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
});
@ -248,7 +255,7 @@ public class SettingsAppearanceActivity extends BaseActivity {
switch(codeBlockList[i]) {
case "White - Black":
tinyDb.putInt("codeBlockColor", getResources().getColor(R.color.white));
tinyDb.putInt("codeBlockColor", getResources().getColor(R.color.colorWhite));
tinyDb.putInt("codeBlockBackground", getResources().getColor(R.color.black));
break;
case "Grey - Black":
@ -256,12 +263,12 @@ public class SettingsAppearanceActivity extends BaseActivity {
tinyDb.putInt("codeBlockBackground", getResources().getColor(R.color.black));
break;
case "White - Grey":
tinyDb.putInt("codeBlockColor", getResources().getColor(R.color.white));
tinyDb.putInt("codeBlockColor", getResources().getColor(R.color.colorWhite));
tinyDb.putInt("codeBlockBackground", getResources().getColor(R.color.colorAccent));
break;
case "Dark - White":
tinyDb.putInt("codeBlockColor", getResources().getColor(R.color.colorPrimary));
tinyDb.putInt("codeBlockBackground", getResources().getColor(R.color.white));
tinyDb.putInt("codeBlockBackground", getResources().getColor(R.color.colorWhite));
break;
default:
tinyDb.putInt("codeBlockColor", getResources().getColor(R.color.colorLightGreen));
@ -270,7 +277,7 @@ public class SettingsAppearanceActivity extends BaseActivity {
}
dialogInterfaceCodeBlock.dismiss();
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
});
@ -307,7 +314,7 @@ public class SettingsAppearanceActivity extends BaseActivity {
}
dialogInterfaceTime.dismiss();
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
});
@ -320,9 +327,7 @@ public class SettingsAppearanceActivity extends BaseActivity {
}
private void initCloseListener() {
onClickListener = view -> {
finish();
};
onClickListener = view -> finish();
}
}

View File

@ -0,0 +1,67 @@
package org.mian.gitnex.activities;
import android.content.Context;
import android.os.Bundle;
import android.view.View;
import android.widget.ImageView;
import android.widget.Switch;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.TinyDB;
/**
* Author M M Arif
*/
public class SettingsDraftsActivity extends BaseActivity {
private Context appCtx;
private View.OnClickListener onClickListener;
@Override
protected int getLayoutResourceId() {
return R.layout.activity_settings_drafts;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
TinyDB tinyDb = new TinyDB(appCtx);
ImageView closeActivity = findViewById(R.id.close);
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
Switch commentsDeletionSwitch = findViewById(R.id.commentsDeletionSwitch);
if(tinyDb.getBoolean("draftsCommentsDeletionEnabled")) {
commentsDeletionSwitch.setChecked(true);
}
else {
commentsDeletionSwitch.setChecked(false);
}
// delete comments on submit switcher
commentsDeletionSwitch.setOnCheckedChangeListener((buttonView, isChecked) -> {
if(isChecked) {
tinyDb.putBoolean("draftsCommentsDeletionEnabled", true);
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
}
else {
tinyDb.putBoolean("draftsCommentsDeletionEnabled", false);
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
}
});
}
private void initCloseListener() { onClickListener = view -> finish(); }
}

View File

@ -9,8 +9,8 @@ import android.widget.Switch;
import android.widget.TextView;
import androidx.appcompat.app.AlertDialog;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.util.TinyDB;
/**
* Author M M Arif
@ -85,7 +85,7 @@ public class SettingsFileViewerActivity extends BaseActivity {
tinyDb.putInt("fileviewerSourceCodeThemeId", i);
dialogInterfaceTheme.dismiss();
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
});
@ -100,12 +100,12 @@ public class SettingsFileViewerActivity extends BaseActivity {
if(isChecked) {
tinyDb.putBoolean("enablePdfMode", true);
tinyDb.putString("enablePdfModeInit", "yes");
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
}
else {
tinyDb.putBoolean("enablePdfMode", false);
tinyDb.putString("enablePdfModeInit", "yes");
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
}
});

View File

@ -6,8 +6,8 @@ import android.view.View;
import android.widget.ImageView;
import android.widget.Switch;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.util.TinyDB;
/**
* Author M M Arif
@ -51,11 +51,11 @@ public class SettingsReportsActivity extends BaseActivity {
if(isChecked) {
tinyDb.putBoolean("crashReportingEnabled", true);
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
}
else {
tinyDb.putBoolean("crashReportingEnabled", false);
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
}
});
@ -63,9 +63,7 @@ public class SettingsReportsActivity extends BaseActivity {
}
private void initCloseListener() {
onClickListener = view -> {
finish();
};
onClickListener = view -> finish();
}
}

View File

@ -7,15 +7,18 @@ import android.util.Log;
import android.view.View;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.NumberPicker;
import android.widget.TextView;
import androidx.appcompat.app.AlertDialog;
import org.apache.commons.io.FileUtils;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.FilesData;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.Version;
import org.mian.gitnex.helpers.ssl.MemorizingTrustManager;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.notifications.NotificationsMaster;
import java.io.File;
import java.io.IOException;
import java.util.HashSet;
@ -27,6 +30,8 @@ import java.util.HashSet;
public class SettingsSecurityActivity extends BaseActivity {
private Context appCtx;
private Context ctx = this;
private View.OnClickListener onClickListener;
private static String[] cacheSizeDataList = {"50 MB", "100 MB", "250 MB", "500 MB", "1 GB"};
@ -35,6 +40,10 @@ public class SettingsSecurityActivity extends BaseActivity {
private static String[] cacheSizeImagesList = {"50 MB", "100 MB", "250 MB", "500 MB", "1 GB"};
private static int cacheSizeImagesSelectedChoice = 0;
private static int MINIMUM_POLLING_DELAY = 1;
private static int DEFAULT_POLLING_DELAY = 20;
private static int MAXIMUM_POLLING_DELAY = 720;
@Override
protected int getLayoutResourceId() {
@ -48,6 +57,7 @@ public class SettingsSecurityActivity extends BaseActivity {
appCtx = getApplicationContext();
TinyDB tinyDb = new TinyDB(appCtx);
String currentVersion = tinyDb.getString("giteaVersion");
ImageView closeActivity = findViewById(R.id.close);
@ -57,8 +67,10 @@ public class SettingsSecurityActivity extends BaseActivity {
TextView cacheSizeDataSelected = findViewById(R.id.cacheSizeDataSelected); // setter for data cache size
TextView cacheSizeImagesSelected = findViewById(R.id.cacheSizeImagesSelected); // setter for images cache size
TextView clearCacheSelected = findViewById(R.id.clearCacheSelected); // setter for clear cache
TextView pollingDelaySelected = findViewById(R.id.pollingDelaySelected);
LinearLayout certsFrame = findViewById(R.id.certsFrame);
LinearLayout pollingDelayFrame = findViewById(R.id.pollingDelayFrame);
LinearLayout cacheSizeDataFrame = findViewById(R.id.cacheSizeDataSelectionFrame);
LinearLayout cacheSizeImagesFrame = findViewById(R.id.cacheSizeImagesSelectionFrame);
LinearLayout clearCacheFrame = findViewById(R.id.clearCacheSelectionFrame);
@ -79,6 +91,12 @@ public class SettingsSecurityActivity extends BaseActivity {
cacheSizeImagesSelectedChoice = tinyDb.getInt("cacheSizeImagesId");
}
if(new Version(currentVersion).less("1.12.3")) {
pollingDelayFrame.setVisibility(View.GONE);
}
pollingDelaySelected.setText(String.format(getString(R.string.pollingDelaySelectedText), tinyDb.getInt("pollingDelayMinutes", DEFAULT_POLLING_DELAY)));
// clear cache setter
File cacheDir = appCtx.getCacheDir();
long size__ = FilesData.getFileSizeRecursively(new HashSet<>(), cacheDir);
@ -137,7 +155,7 @@ public class SettingsSecurityActivity extends BaseActivity {
tinyDb.putInt("cacheSizeImagesId", i);
dialogInterfaceTheme.dismiss();
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
});
@ -167,7 +185,7 @@ public class SettingsSecurityActivity extends BaseActivity {
tinyDb.putInt("cacheSizeId", i);
dialogInterfaceTheme.dismiss();
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
});
@ -190,7 +208,6 @@ public class SettingsSecurityActivity extends BaseActivity {
tinyDb.putBoolean("loggedInMode", false);
tinyDb.remove("basicAuthPassword");
tinyDb.putBoolean("basicAuthFlag", false);
//tinyDb.clear();
Intent loginActivityIntent = new Intent().setClass(appCtx, LoginActivity.class);
loginActivityIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
@ -203,12 +220,42 @@ public class SettingsSecurityActivity extends BaseActivity {
});
// polling delay
pollingDelayFrame.setOnClickListener(v -> {
NumberPicker numberPicker = new NumberPicker(ctx);
numberPicker.setMinValue(MINIMUM_POLLING_DELAY);
numberPicker.setMaxValue(MAXIMUM_POLLING_DELAY);
numberPicker.setValue(tinyDb.getInt("pollingDelayMinutes", DEFAULT_POLLING_DELAY));
numberPicker.setWrapSelectorWheel(true);
AlertDialog.Builder builder = new AlertDialog.Builder(ctx);
builder.setTitle(getString(R.string.pollingDelayDialogHeaderText));
builder.setMessage(getString(R.string.pollingDelayDialogDescriptionText));
builder.setCancelable(true);
builder.setPositiveButton(getString(R.string.okButton), (dialog, which) -> {
tinyDb.putInt("pollingDelayMinutes", numberPicker.getValue());
NotificationsMaster.fireWorker(ctx);
NotificationsMaster.hireWorker(ctx);
pollingDelaySelected.setText(String.format(getString(R.string.pollingDelaySelectedText), numberPicker.getValue()));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
});
builder.setNeutralButton(R.string.cancelButton, null);
builder.setView(numberPicker);
builder.create().show();
});
}
private void initCloseListener() {
onClickListener = view -> {
finish();
};
}
onClickListener = view -> finish();
}
}

View File

@ -10,8 +10,8 @@ import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.appcompat.app.AlertDialog;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.util.TinyDB;
/**
* Author M M Arif
@ -22,8 +22,8 @@ public class SettingsTranslationActivity extends BaseActivity {
private Context appCtx;
private View.OnClickListener onClickListener;
private static String[] langList = {"English", "Arabic", "Chinese", "Finnish", "French", "German", "Italian", "Latvian", "Persian", "Polish", "Portuguese/Brazilian", "Russian", "Serbian", "Spanish", "Turkish",
"Ukrainian"};
private static String[] langList = {"English", "Arabic", "Chinese", "Czech", "Finnish", "French", "German", "Italian", "Latvian", "Persian",
"Polish", "Portuguese/Brazilian", "Russian", "Serbian", "Spanish", "Turkish", "Ukrainian"};
private static int langSelectedChoice = 0;
@Override
@ -95,6 +95,9 @@ public class SettingsTranslationActivity extends BaseActivity {
case "Chinese":
tinyDb.putString("locale", "zh");
break;
case "Czech":
tinyDb.putString("locale", "cs");
break;
case "Finnish":
tinyDb.putString("locale", "fi");
break;
@ -143,11 +146,11 @@ public class SettingsTranslationActivity extends BaseActivity {
this.recreate();
this.overridePendingTransition(0, 0);
dialogInterface.dismiss();
Toasty.info(appCtx, getResources().getString(R.string.settingsSave));
Toasty.success(appCtx, getResources().getString(R.string.settingsSave));
});
lBuilder.setNegativeButton(getString(R.string.cancelButton), (dialog, which) -> dialog.dismiss());
lBuilder.setNeutralButton(getString(R.string.cancelButton), null);
AlertDialog lDialog = lBuilder.create();
lDialog.show();
@ -157,9 +160,8 @@ public class SettingsTranslationActivity extends BaseActivity {
}
private void initCloseListener() {
onClickListener = view -> {
finish();
};
onClickListener = view -> finish();
}
}

View File

@ -1,70 +0,0 @@
package org.mian.gitnex.activities;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import android.content.Context;
import android.content.res.Resources;
import android.os.Bundle;
import android.view.View;
import android.widget.ImageView;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.SponsorsAdapter;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
/**
* Author M M Arif
*/
public class SponsorsActivity extends BaseActivity {
private View.OnClickListener onClickListener;
private Context appCtx;
@Override
protected int getLayoutResourceId(){
return R.layout.activity_sponsors;
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
appCtx = getApplicationContext();
ImageView closeActivity = findViewById(R.id.close);
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
Resources res = getResources();
CharSequence[] sponsorsInfo = res.getTextArray(R.array.sponsorsInfo);
List<CharSequence> sponsorsList = new ArrayList<>(Arrays.asList(sponsorsInfo));
RecyclerView mRecyclerView = findViewById(R.id.recyclerView);
mRecyclerView.setHasFixedSize(true);
mRecyclerView.setLayoutManager(new LinearLayoutManager(appCtx));
DividerItemDecoration dividerItemDecoration = new DividerItemDecoration(mRecyclerView.getContext(),
DividerItemDecoration.VERTICAL);
mRecyclerView.addItemDecoration(dividerItemDecoration);
SponsorsAdapter adapter = new SponsorsAdapter(sponsorsList);
mRecyclerView.setAdapter(adapter);
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
}
}

View File

@ -86,7 +86,7 @@ public class AdminGetUsersAdapter extends RecyclerView.Adapter<AdminGetUsersAdap
holder.userRole.setVisibility(View.VISIBLE);
TextDrawable drawable = TextDrawable.builder()
.beginConfig()
.textColor(mCtx.getResources().getColor(R.color.white))
.textColor(mCtx.getResources().getColor(R.color.colorWhite))
.fontSize(44)
.width(180)
.height(60)

View File

@ -1,90 +0,0 @@
package org.mian.gitnex.adapters;
import android.content.Context;
import android.content.Intent;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Button;
import android.widget.TextView;
import org.mian.gitnex.R;
import org.mian.gitnex.activities.CommitsActivity;
import org.mian.gitnex.models.Branches;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
import java.util.Objects;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
/**
* Author M M Arif
*/
public class BranchesAdapter extends RecyclerView.Adapter<BranchesAdapter.BranchesViewHolder> {
private List<Branches> branchesList;
private Context mCtx;
static class BranchesViewHolder extends RecyclerView.ViewHolder {
private TextView branchNameTv;
private TextView branchCommitAuthor;
private BranchesViewHolder(View itemView) {
super(itemView);
branchNameTv = itemView.findViewById(R.id.branchName);
branchCommitAuthor = itemView.findViewById(R.id.branchCommitAuthor);
Button branchCommitHash = itemView.findViewById(R.id.branchCommitHash);
branchCommitHash.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
Intent intent = new Intent(v.getContext(), CommitsActivity.class);
intent.putExtra("branchName", String.valueOf(branchNameTv.getText()));
Objects.requireNonNull(v.getContext()).startActivity(intent);
}
});
}
}
public BranchesAdapter(Context mCtx, List<Branches> branchesMain) {
this.mCtx = mCtx;
this.branchesList = branchesMain;
}
@NonNull
@Override
public BranchesAdapter.BranchesViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_branches, parent, false);
return new BranchesAdapter.BranchesViewHolder(v);
}
@Override
public void onBindViewHolder(@NonNull BranchesAdapter.BranchesViewHolder holder, int position) {
final TinyDB tinyDb = new TinyDB(mCtx);
final String instanceUrl = tinyDb.getString("instanceUrl");
Branches currentItem = branchesList.get(position);
holder.branchNameTv.setText(currentItem.getName());
if(currentItem.getCommit().getAuthor().getName() != null || !currentItem.getCommit().getAuthor().getName().equals("")) {
holder.branchCommitAuthor.setText(mCtx.getResources().getString(R.string.commitAuthor, currentItem.getCommit().getAuthor().getName()));
}
else {
holder.branchCommitAuthor.setText(mCtx.getResources().getString(R.string.commitAuthor, currentItem.getCommit().getAuthor().getUsername()));
}
}
@Override
public int getItemCount() {
return branchesList.size();
}
}

View File

@ -14,8 +14,8 @@ import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.ClickListener;
import org.mian.gitnex.helpers.TimeHelper;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.Commits;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
import java.util.Locale;

View File

@ -0,0 +1,158 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.Context;
import android.content.Intent;
import android.text.Html;
import android.text.Spanned;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.activities.ReplyToIssueActivity;
import org.mian.gitnex.database.api.DraftsApi;
import org.mian.gitnex.database.models.DraftWithRepository;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import java.util.List;
/**
* Author M M Arif
*/
public class DraftsAdapter extends RecyclerView.Adapter<DraftsAdapter.DraftsViewHolder> {
private List<DraftWithRepository> draftsList;
private Context mCtx;
class DraftsViewHolder extends RecyclerView.ViewHolder {
private TextView draftText;
private TextView repoInfo;
private TextView repoId;
private TextView draftId;
private TextView issueNumber;
private TextView issueType;
private TextView repoOwner;
private TextView repoName;
private TextView commentId;
private ImageView editCommentStatus;
private DraftsViewHolder(View itemView) {
super(itemView);
draftText = itemView.findViewById(R.id.draftText);
repoInfo = itemView.findViewById(R.id.repoInfo);
repoId = itemView.findViewById(R.id.repoId);
draftId = itemView.findViewById(R.id.draftId);
issueNumber = itemView.findViewById(R.id.issueNumber);
issueType = itemView.findViewById(R.id.issueType);
repoOwner = itemView.findViewById(R.id.repoOwner);
repoName = itemView.findViewById(R.id.repoName);
commentId = itemView.findViewById(R.id.commentId);
ImageView deleteDraft = itemView.findViewById(R.id.deleteDraft);
editCommentStatus = itemView.findViewById(R.id.editCommentStatus);
deleteDraft.setOnClickListener(itemDelete -> {
int getDraftId = Integer.parseInt(draftId.getText().toString());
deleteDraft(getAdapterPosition());
DraftsApi draftsApi = new DraftsApi(mCtx);
draftsApi.deleteSingleDraft(getDraftId);
});
itemView.setOnClickListener(itemEdit -> {
Intent intent = new Intent(mCtx, ReplyToIssueActivity.class);
intent.putExtra("commentBody", draftText.getText().toString());
intent.putExtra("issueNumber", issueNumber.getText().toString());
intent.putExtra("repositoryId", repoId.getText().toString());
intent.putExtra("draftTitle", repoInfo.getText().toString());
intent.putExtra("commentId", commentId.getText().toString());
intent.putExtra("draftId", draftId.getText().toString());
if(!commentId.getText().toString().equalsIgnoreCase("")) {
intent.putExtra("commentAction", "edit");
}
TinyDB tinyDb = new TinyDB(mCtx);
tinyDb.putString("issueNumber", issueNumber.getText().toString());
tinyDb.putLong("repositoryId", Long.parseLong(repoId.getText().toString()));
//tinyDb.putString("issueType", issueType.getText().toString());
mCtx.startActivity(intent);
});
}
}
public DraftsAdapter(Context mCtx, List<DraftWithRepository> draftsListMain) {
this.mCtx = mCtx;
this.draftsList = draftsListMain;
}
private void deleteDraft(int position) {
draftsList.remove(position);
notifyItemRemoved(position);
notifyItemRangeChanged(position, draftsList.size());
Toasty.success(mCtx, mCtx.getResources().getString(R.string.draftsSingleDeleteSuccess));
}
@NonNull
@Override
public DraftsAdapter.DraftsViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_drafts, parent, false);
return new DraftsViewHolder(v);
}
@SuppressLint("DefaultLocale")
@Override
public void onBindViewHolder(@NonNull DraftsAdapter.DraftsViewHolder holder, int position) {
DraftWithRepository currentItem = draftsList.get(position);
holder.repoId.setText(String.valueOf(currentItem.getRepositoryId()));
holder.draftId.setText(String.valueOf(currentItem.getDraftId()));
holder.issueNumber.setText(String.valueOf(currentItem.getIssueId()));
holder.issueType.setText(currentItem.getDraftType());
holder.repoOwner.setText(currentItem.getRepositoryOwner());
holder.repoName.setText(currentItem.getRepositoryName());
holder.draftText.setText(currentItem.getDraftText());
holder.commentId.setText(currentItem.getCommentId());
String issueNumber = "<font color='" + mCtx.getResources().getColor(R.color.lightGray) + "'>" + mCtx.getResources().getString(R.string.hash) + currentItem.getIssueId() + "</font>";
Spanned headTitle = Html.fromHtml(issueNumber + " " + currentItem.getRepositoryOwner() + " / " + currentItem.getRepositoryName());
holder.repoInfo.setText(headTitle);
if(!currentItem.getCommentId().equalsIgnoreCase("new")) {
holder.editCommentStatus.setVisibility(View.VISIBLE);
}
else {
holder.editCommentStatus.setVisibility(View.GONE);
}
}
@Override
public int getItemCount() {
return draftsList.size();
}
public void updateList(List<DraftWithRepository> list) {
draftsList = list;
notifyDataSetChanged();
}
}

View File

@ -1,6 +1,8 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.ClipData;
import android.content.ClipboardManager;
import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
@ -9,6 +11,7 @@ import android.view.View;
import android.view.ViewGroup;
import android.widget.CheckBox;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
@ -18,16 +21,20 @@ import com.google.android.material.bottomsheet.BottomSheetDialog;
import org.mian.gitnex.R;
import org.mian.gitnex.activities.OpenRepoInBrowserActivity;
import org.mian.gitnex.activities.RepoDetailActivity;
import org.mian.gitnex.activities.RepoForksActivity;
import org.mian.gitnex.activities.RepoStargazersActivity;
import org.mian.gitnex.activities.RepoWatchersActivity;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.RepositoriesApi;
import org.mian.gitnex.database.models.Repository;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.UserRepositories;
import org.mian.gitnex.models.WatchInfo;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
import java.util.Objects;
import retrofit2.Call;
import retrofit2.Callback;
@ -37,7 +44,6 @@ import retrofit2.Callback;
public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepositoriesAdapter.ReposSearchViewHolder> {
private List<UserRepositories> searchedReposList;
private Context mCtx;
@ -58,6 +64,10 @@ public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepo
private TextView repoStars;
private TextView repoForks;
private TextView repoOpenIssuesCount;
private TextView repoType;
private LinearLayout archiveRepo;
private TextView repoBranch;
private TextView htmlUrl;
private ReposSearchViewHolder(View itemView) {
@ -73,6 +83,10 @@ public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepo
repoForks = itemView.findViewById(R.id.repoForks);
repoOpenIssuesCount = itemView.findViewById(R.id.repoOpenIssuesCount);
ImageView reposDropdownMenu = itemView.findViewById(R.id.reposDropdownMenu);
repoType = itemView.findViewById(R.id.repoType);
archiveRepo = itemView.findViewById(R.id.archiveRepoFrame);
repoBranch = itemView.findViewById(R.id.repoBranch);
htmlUrl = itemView.findViewById(R.id.htmlUrl);
itemView.setOnClickListener(v -> {
@ -86,13 +100,35 @@ public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepo
tinyDb.putString("repoFullName", repoFullName.getText().toString());
tinyDb.putBoolean("resumeIssues", true);
tinyDb.putBoolean("isRepoAdmin", isRepoAdmin.isChecked());
tinyDb.putString("repoBranch", repoBranch.getText().toString());
String[] parts = fullName.getText().toString().split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
int currentActiveAccountId = tinyDb.getInt("currentActiveAccountId");
RepositoriesApi repositoryData = new RepositoriesApi(context);
//RepositoriesRepository.deleteRepositoriesByAccount(currentActiveAccountId);
Integer count = repositoryData.checkRepository(currentActiveAccountId, repoOwner, repoName);
if(count == 0) {
long id = repositoryData.insertRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", id);
}
else {
Repository data = repositoryData.getRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", data.getRepositoryId());
}
//store if user is watching this repo
{
final String instanceUrl = tinyDb.getString("instanceUrl");
String[] parts = repoFullName.getText().toString().split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
final String token = "token " + tinyDb.getString(tinyDb.getString("loginUid") + "-token");
WatchInfo watch = new WatchInfo();
@ -117,7 +153,7 @@ public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepo
if(response.code() != 404) {
Toasty.info(context, context.getString(R.string.genericApiStatusError));
Toasty.error(context, context.getString(R.string.genericApiStatusError));
}
@ -129,10 +165,11 @@ public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepo
public void onFailure(@NonNull Call<WatchInfo> call, @NonNull Throwable t) {
tinyDb.putBoolean("repoWatch", false);
Toasty.info(context, context.getString(R.string.genericApiStatusError));
Toasty.error(context, context.getString(R.string.genericApiStatusError));
}
});
}
context.startActivity(intent);
@ -148,13 +185,26 @@ public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepo
TextView repoOpenInBrowser = view.findViewById(R.id.repoOpenInBrowser);
TextView repoStargazers = view.findViewById(R.id.repoStargazers);
TextView repoWatchers = view.findViewById(R.id.repoWatchers);
TextView repoForksList = view.findViewById(R.id.repoForksList);
TextView repoCopyUrl = view.findViewById(R.id.repoCopyUrl);
TextView bottomSheetHeader = view.findViewById(R.id.bottomSheetHeader);
bottomSheetHeader.setText(fullName.getText());
bottomSheetHeader.setText(String.format("%s / %s", fullName.getText().toString().split("/")[0], fullName.getText().toString().split("/")[1]));
BottomSheetDialog dialog = new BottomSheetDialog(context);
dialog.setContentView(view);
dialog.show();
repoCopyUrl.setOnClickListener(openInBrowser -> {
ClipboardManager clipboard = (ClipboardManager) Objects.requireNonNull(context).getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText("repoUrl", htmlUrl.getText().toString());
assert clipboard != null;
clipboard.setPrimaryClip(clip);
Toasty.info(context, context.getString(R.string.copyIssueUrlToastMsg));
dialog.dismiss();
});
repoOpenInBrowser.setOnClickListener(openInBrowser -> {
Intent intentOpenInBrowser = new Intent(context, OpenRepoInBrowserActivity.class);
@ -182,6 +232,15 @@ public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepo
});
repoForksList.setOnClickListener(forks -> {
Intent intentW = new Intent(context, RepoForksActivity.class);
intentW.putExtra("repoFullNameForForks", fullName.getText());
context.startActivity(intentW);
dialog.dismiss();
});
});
}
@ -199,10 +258,10 @@ public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepo
@Override
public void onBindViewHolder(@NonNull final ExploreRepositoriesAdapter.ReposSearchViewHolder holder, int position) {
final UserRepositories currentItem = searchedReposList.get(position);
UserRepositories currentItem = searchedReposList.get(position);
holder.repoDescription.setVisibility(View.GONE);
holder.repoBranch.setText(currentItem.getDefault_branch());
holder.htmlUrl.setText(currentItem.getHtml_url());
ColorGenerator generator = ColorGenerator.MATERIAL;
int color = generator.getColor(currentItem.getName());
@ -227,12 +286,14 @@ public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepo
holder.repoDescription.setVisibility(View.VISIBLE);
holder.repoDescription.setText(currentItem.getDescription());
}
holder.fullName.setText(currentItem.getFullname());
holder.fullName.setText(currentItem.getFullName());
if(currentItem.getPrivateFlag()) {
holder.repoPrivatePublic.setImageResource(R.drawable.ic_lock_bold);
holder.repoPrivatePublic.setImageResource(R.drawable.ic_lock);
holder.repoType.setText(R.string.strPrivate);
}
else {
holder.repoPrivatePublic.setImageResource(R.drawable.ic_public);
holder.repoPrivatePublic.setVisibility(View.GONE);
holder.repoType.setText(R.string.strPublic);
}
holder.repoStars.setText(currentItem.getStars_count());
holder.repoForks.setText(currentItem.getForks_count());
@ -242,6 +303,13 @@ public class ExploreRepositoriesAdapter extends RecyclerView.Adapter<ExploreRepo
}
holder.isRepoAdmin.setChecked(currentItem.getPermissions().isAdmin());
if(currentItem.isArchived()) {
holder.archiveRepo.setVisibility(View.VISIBLE);
}
else {
holder.archiveRepo.setVisibility(View.GONE);
}
}
@Override

View File

@ -11,9 +11,9 @@ import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.Files;
import org.mian.gitnex.util.AppUtil;
import java.util.ArrayList;
import java.util.List;
@ -37,6 +37,8 @@ public class FilesAdapter extends RecyclerView.Adapter<FilesAdapter.FilesViewHol
class FilesViewHolder extends RecyclerView.ViewHolder {
private ImageView fileTypeImage;
private ImageView dirTypeImage;
private ImageView unknownTypeImage;
private TextView fileName;
private TextView fileType;
private TextView fileInfo;
@ -46,14 +48,14 @@ public class FilesAdapter extends RecyclerView.Adapter<FilesAdapter.FilesViewHol
super(itemView);
fileName = itemView.findViewById(R.id.fileName);
fileTypeImage = itemView.findViewById(R.id.fileImage);
dirTypeImage = itemView.findViewById(R.id.dirImage);
unknownTypeImage = itemView.findViewById(R.id.unknownImage);
fileType = itemView.findViewById(R.id.fileType);
fileInfo = itemView.findViewById(R.id.fileInfo);
//ImageView filesDropdownMenu = itemView.findViewById(R.id.filesDropdownMenu);
fileName.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
fileName.setOnClickListener(v -> {
Context context = v.getContext();
@ -64,10 +66,9 @@ public class FilesAdapter extends RecyclerView.Adapter<FilesAdapter.FilesViewHol
filesListener.onClickDir(fileName.getText().toString());
}
else {
Toasty.info(context, context.getString(R.string.filesGenericError));
Toasty.warning(context, context.getString(R.string.filesGenericError));
}
}
});
@ -160,15 +161,22 @@ public class FilesAdapter extends RecyclerView.Adapter<FilesAdapter.FilesViewHol
holder.fileName.setText(currentItem.getName());
if(currentItem.getType().equals("file")) {
holder.fileTypeImage.setImageDrawable(mCtx.getResources().getDrawable(R.drawable.ic_file_new));
holder.fileTypeImage.setVisibility(View.VISIBLE);
holder.dirTypeImage.setVisibility(View.GONE);
holder.unknownTypeImage.setVisibility(View.GONE);
holder.fileInfo.setVisibility(View.VISIBLE);
holder.fileInfo.setText(AppUtil.formatFileSizeInDetail(currentItem.getSize()));
}
else if(currentItem.getType().equals("dir")) {
holder.fileTypeImage.setImageDrawable(mCtx.getResources().getDrawable(R.drawable.ic_folder_24));
holder.dirTypeImage.setVisibility(View.VISIBLE);
holder.unknownTypeImage.setVisibility(View.GONE);
holder.fileTypeImage.setVisibility(View.GONE);
holder.fileInfo.setVisibility(View.GONE);
}
else {
holder.fileTypeImage.setImageDrawable(mCtx.getResources().getDrawable(R.drawable.ic_question_mark_24));
holder.unknownTypeImage.setVisibility(View.VISIBLE);
holder.dirTypeImage.setVisibility(View.GONE);
holder.fileTypeImage.setVisibility(View.GONE);
}
}

View File

@ -86,7 +86,7 @@ public class FilesDiffAdapter extends BaseAdapter {
FileDiffView data = (FileDiffView) getItem(position);
headerFileName.setText(data.getFileName());
if(data.isFileType()) {
if(data.isFileBinary()) {
diffStats.setVisibility(View.GONE);
diffLines.addView(getMessageView(context.getResources().getString(R.string.binaryFileError)));
@ -97,7 +97,7 @@ public class FilesDiffAdapter extends BaseAdapter {
diffStats.setVisibility(View.VISIBLE);
headerFileInfo.setText(data.getFileInfo());
String[] codeLines = getLines(data.getFileContents());
String[] codeLines = getLines(data.toString());
if(MAXIMUM_LINES > codeLines.length) {

View File

@ -1,6 +1,8 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.ClipData;
import android.content.ClipboardManager;
import android.content.Context;
import android.content.Intent;
import android.graphics.drawable.Drawable;
@ -24,10 +26,10 @@ import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.ClickListener;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TimeHelper;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.helpers.UserMentions;
import org.mian.gitnex.models.IssueComments;
import org.mian.gitnex.util.TinyDB;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
@ -104,13 +106,20 @@ public class IssueCommentsAdapter extends RecyclerView.Adapter<IssueCommentsAdap
TextView commentMenuEdit = view.findViewById(R.id.commentMenuEdit);
TextView commentShare = view.findViewById(R.id.issueCommentShare);
TextView commentMenuQuote = view.findViewById(R.id.commentMenuQuote);
TextView commentMenuCopy = view.findViewById(R.id.commentMenuCopy);
TextView commentMenuDelete = view.findViewById(R.id.commentMenuDelete);
TextView issueCommentCopyUrl = view.findViewById(R.id.issueCommentCopyUrl);
if(!loginUid.contentEquals(commenterUsername.getText())) {
commentMenuEdit.setVisibility(View.GONE);
commentMenuDelete.setVisibility(View.GONE);
}
if(issueComment.getText().toString().isEmpty()) {
commentMenuCopy.setVisibility(View.GONE);
}
BottomSheetDialog dialog = new BottomSheetDialog(ctx);
dialog.setContentView(view);
dialog.show();
@ -143,6 +152,64 @@ public class IssueCommentsAdapter extends RecyclerView.Adapter<IssueCommentsAdap
});
issueCommentCopyUrl.setOnClickListener(ediComment -> {
// comment Url
CharSequence commentUrl = htmlUrl.getText();
ClipboardManager clipboard = (ClipboardManager) Objects.requireNonNull(ctx).getSystemService(Context.CLIPBOARD_SERVICE);
assert clipboard != null;
ClipData clip = ClipData.newPlainText(commentUrl, commentUrl);
clipboard.setPrimaryClip(clip);
dialog.dismiss();
Toasty.success(ctx, ctx.getString(R.string.copyIssueUrlToastMsg));
});
commentMenuQuote.setOnClickListener(v1 -> {
StringBuilder stringBuilder = new StringBuilder();
String commenterName = commenterUsername.getText().toString();
if(!commenterName.equals(tinyDb.getString("userLogin"))) {
stringBuilder.append("@").append(commenterName).append("\n\n");
}
String[] lines = commendBodyRaw.getText().toString().split("\\R");
for(String line : lines) {
stringBuilder.append(">").append(line).append("\n");
}
stringBuilder.append("\n");
Intent intent = new Intent(ctx, ReplyToIssueActivity.class);
intent.putExtra("commentBody", stringBuilder.toString());
intent.putExtra("cursorToEnd", true);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
dialog.dismiss();
ctx.startActivity(intent);
});
commentMenuCopy.setOnClickListener(view1 -> {
ClipboardManager clipboard = (ClipboardManager) Objects.requireNonNull(ctx).getSystemService(Context.CLIPBOARD_SERVICE);
assert clipboard != null;
ClipData clip = ClipData.newPlainText("Comment on issue #" + issueNumber.getText().toString(), issueComment.getText().toString());
clipboard.setPrimaryClip(clip);
dialog.dismiss();
Toasty.success(ctx, ctx.getString(R.string.copyIssueCommentToastMsg));
});
commentMenuDelete.setOnClickListener(deleteComment -> {
deleteIssueComment(ctx, Integer.parseInt(commendId.getText().toString()), getAdapterPosition());
@ -192,7 +259,7 @@ public class IssueCommentsAdapter extends RecyclerView.Adapter<IssueCommentsAdap
if(response.code() == 204) {
updateAdapter(position);
Toasty.info(ctx, ctx.getResources().getString(R.string.deleteCommentSuccess));
Toasty.success(ctx, ctx.getResources().getString(R.string.deleteCommentSuccess));
}
else if(response.code() == 401) {
@ -205,17 +272,17 @@ public class IssueCommentsAdapter extends RecyclerView.Adapter<IssueCommentsAdap
}
else if(response.code() == 403) {
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
Toasty.error(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
Toasty.info(ctx, ctx.getString(R.string.apiNotFound));
Toasty.warning(ctx, ctx.getString(R.string.apiNotFound));
}
else {
Toasty.info(ctx, ctx.getString(R.string.genericError));
Toasty.error(ctx, ctx.getString(R.string.genericError));
}

View File

@ -18,8 +18,8 @@ import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.helpers.ClickListener;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TimeHelper;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.Issues;
import org.mian.gitnex.util.TinyDB;
import org.ocpsoft.prettytime.PrettyTime;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
@ -125,7 +125,7 @@ public class IssuesAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder>
TinyDB tinyDb = new TinyDB(context);
tinyDb.putString("issueNumber", issueNumber.getText().toString());
tinyDb.putString("issueType", "issue");
tinyDb.putString("issueType", "Issue");
context.startActivity(intent);
});
@ -138,7 +138,7 @@ public class IssuesAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder>
TinyDB tinyDb = new TinyDB(context);
tinyDb.putString("issueNumber", issueNumber.getText().toString());
tinyDb.putString("issueType", "issue");
tinyDb.putString("issueType", "Issue");
context.startActivity(intent);
});

View File

@ -3,26 +3,25 @@ package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.Context;
import android.content.Intent;
import android.content.res.ColorStateList;
import android.graphics.Color;
import android.graphics.Typeface;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.TextView;
import com.amulyakhare.textdrawable.TextDrawable;
import androidx.annotation.NonNull;
import androidx.cardview.widget.CardView;
import androidx.core.widget.ImageViewCompat;
import androidx.recyclerview.widget.RecyclerView;
import com.google.android.material.bottomsheet.BottomSheetDialog;
import org.mian.gitnex.R;
import org.mian.gitnex.activities.CreateLabelActivity;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.ColorInverter;
import org.mian.gitnex.helpers.LabelWidthCalculator;
import org.mian.gitnex.models.Labels;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
/**
* Author M M Arif
@ -39,12 +38,17 @@ public class LabelsAdapter extends RecyclerView.Adapter<LabelsAdapter.LabelsView
private TextView labelTitle;
private TextView labelId;
private TextView labelColor;
private ImageView labelsView;
private CardView labelView;
private ImageView labelIcon;
private TextView labelName;
private LabelsViewHolder(View itemView) {
super(itemView);
labelsView = itemView.findViewById(R.id.labelsView);
labelView = itemView.findViewById(R.id.labelView);
labelIcon = itemView.findViewById(R.id.labelIcon);
labelName = itemView.findViewById(R.id.labelName);
ImageView labelsOptionsMenu = itemView.findViewById(R.id.labelsOptionsMenu);
labelTitle = itemView.findViewById(R.id.labelTitle);
labelId = itemView.findViewById(R.id.labelId);
@ -119,19 +123,13 @@ public class LabelsAdapter extends RecyclerView.Adapter<LabelsAdapter.LabelsView
String labelName = currentItem.getName();
int color = Color.parseColor("#" + labelColor);
int contrastColor = new ColorInverter().getContrastColor(color);
TextDrawable drawable = TextDrawable.builder()
.beginConfig()
.useFont(Typeface.DEFAULT)
.bold()
.textColor(new ColorInverter().getContrastColor(color))
.fontSize(35)
.width(LabelWidthCalculator.calculateLabelWidth(labelName, Typeface.DEFAULT, 40, 20))
.height(55)
.endConfig()
.buildRoundRect(labelName, color, 10);
ImageViewCompat.setImageTintList(holder.labelIcon, ColorStateList.valueOf(contrastColor));
holder.labelsView.setImageDrawable(drawable);
holder.labelName.setTextColor(contrastColor);
holder.labelName.setText(labelName);
holder.labelView.setCardBackgroundColor(color);
}

View File

@ -0,0 +1,95 @@
package org.mian.gitnex.adapters;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.CheckBox;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.models.Labels;
import java.util.ArrayList;
import java.util.List;
/**
* Author M M Arif
*/
public class LabelsListAdapter extends RecyclerView.Adapter<LabelsListAdapter.LabelsViewHolder> {
private List<Labels> labels;
private ArrayList<String> labelsStrings = new ArrayList<>();
private ArrayList<Integer> labelsIds = new ArrayList<>();
private LabelsListAdapterListener labelsListener;
public interface LabelsListAdapterListener {
void labelsStringData(ArrayList<String> data);
void labelsIdsData(ArrayList<Integer> data);
}
public LabelsListAdapter(List<Labels> labelsMain, LabelsListAdapterListener labelsListener) {
this.labels = labelsMain;
this.labelsListener = labelsListener;
}
static class LabelsViewHolder extends RecyclerView.ViewHolder {
private CheckBox labelSelection;
private LabelsViewHolder(View itemView) {
super(itemView);
labelSelection = itemView.findViewById(R.id.labelSelection);
}
}
@NonNull
@Override
public LabelsListAdapter.LabelsViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.custom_labels_list, parent, false);
return new LabelsListAdapter.LabelsViewHolder(v);
}
@Override
public void onBindViewHolder(@NonNull LabelsListAdapter.LabelsViewHolder holder, int position) {
Labels currentItem = labels.get(position);
holder.labelSelection.setText(currentItem.getName());
for(int i = 0; i < labelsIds.size(); i++) {
if(labelsStrings.contains(currentItem.getName())) {
holder.labelSelection.setChecked(true);
}
}
holder.labelSelection.setOnCheckedChangeListener((buttonView, isChecked) -> {
if(isChecked) {
labelsStrings.add(currentItem.getName());
labelsIds.add(currentItem.getId());
}
else {
labelsStrings.remove(currentItem.getName());
labelsIds.remove(Integer.valueOf(currentItem.getId()));
}
labelsListener.labelsStringData(labelsStrings);
labelsListener.labelsIdsData(labelsIds);
});
}
@Override
public int getItemCount() {
return labels.size();
}
}

View File

@ -2,7 +2,6 @@ package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.Context;
import android.graphics.Color;
import android.graphics.drawable.Drawable;
import android.net.Uri;
import android.text.Spanned;
@ -15,7 +14,6 @@ import android.widget.ProgressBar;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import com.amulyakhare.textdrawable.TextDrawable;
import com.google.android.material.bottomsheet.BottomSheetDialog;
import com.vdurmont.emoji.EmojiParser;
import org.mian.gitnex.R;
@ -23,8 +21,8 @@ import org.mian.gitnex.actions.MilestoneActions;
import org.mian.gitnex.helpers.ClickListener;
import org.mian.gitnex.helpers.StaticGlobalVariables;
import org.mian.gitnex.helpers.TimeHelper;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.Milestones;
import org.mian.gitnex.util.TinyDB;
import java.text.DateFormat;
import java.text.ParseException;
import java.text.SimpleDateFormat;
@ -112,7 +110,6 @@ public class MilestonesAdapter extends RecyclerView.Adapter<RecyclerView.ViewHol
private TextView msOpenIssues;
private TextView msClosedIssues;
private TextView msDueDate;
private ImageView msStatus;
private ProgressBar msProgress;
private TextView milestoneStatus;
@ -122,7 +119,6 @@ public class MilestonesAdapter extends RecyclerView.Adapter<RecyclerView.ViewHol
milestoneId = itemView.findViewById(R.id.milestoneId);
msTitle = itemView.findViewById(R.id.milestoneTitle);
msStatus = itemView.findViewById(R.id.milestoneState);
msDescription = itemView.findViewById(R.id.milestoneDescription);
msOpenIssues = itemView.findViewById(R.id.milestoneIssuesOpen);
msClosedIssues = itemView.findViewById(R.id.milestoneIssuesClosed);
@ -188,10 +184,9 @@ public class MilestonesAdapter extends RecyclerView.Adapter<RecyclerView.ViewHol
milestoneId.setText(String.valueOf(dataModel.getId()));
milestoneStatus.setText(dataModel.getState());
final Markwon markwon = Markwon.builder(Objects.requireNonNull(context))
.usePlugin(CorePlugin.create())
.usePlugin(ImagesPlugin.create(plugin -> {
Markwon markwon = Markwon.builder(Objects.requireNonNull(context)).usePlugin(CorePlugin.create()).usePlugin(ImagesPlugin.create(plugin -> {
plugin.addSchemeHandler(new SchemeHandler() {
@NonNull
@Override
public ImageItem handle(@NonNull String raw, @NonNull Uri uri) {
@ -213,13 +208,16 @@ public class MilestonesAdapter extends RecyclerView.Adapter<RecyclerView.ViewHol
return Collections.singleton("drawable");
}
});
plugin.placeholderProvider(drawable -> null);
plugin.addMediaDecoder(GifMediaDecoder.create(false));
plugin.addMediaDecoder(SvgMediaDecoder.create(context.getResources()));
plugin.addMediaDecoder(SvgMediaDecoder.create());
plugin.defaultMediaDecoder(DefaultMediaDecoder.create(context.getResources()));
plugin.defaultMediaDecoder(DefaultMediaDecoder.create());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@Override
public void configureTheme(@NonNull MarkwonTheme.Builder builder) {
@ -239,71 +237,42 @@ public class MilestonesAdapter extends RecyclerView.Adapter<RecyclerView.ViewHol
Spanned msTitle_ = markwon.toMarkdown(dataModel.getTitle());
markwon.setParsedMarkdown(msTitle, msTitle_);
if(dataModel.getState().equals("open")) {
@SuppressLint("ResourceType") int color = Color.parseColor(context.getResources().getString(R.color.releaseStable));
TextDrawable drawable = TextDrawable.builder()
.beginConfig()
//.useFont(Typeface.DEFAULT)
.textColor(context.getResources().getColor(R.color.white))
.fontSize(30)
.toUpperCase()
.width(120)
.height(60)
.endConfig()
.buildRoundRect("open", color, 8);
msStatus.setImageDrawable(drawable);
}
else if(dataModel.getState().equals("closed")) {
@SuppressLint("ResourceType") int color = Color.parseColor(context.getResources().getString(R.color.colorRed));
TextDrawable drawable = TextDrawable.builder()
.beginConfig()
//.useFont(Typeface.DEFAULT)
.textColor(context.getResources().getColor(R.color.white))
.fontSize(30)
.toUpperCase()
.width(140)
.height(60)
.endConfig()
.buildRoundRect("closed", color, 8);
msStatus.setImageDrawable(drawable);
}
if(!dataModel.getDescription().equals("")) {
final CharSequence bodyWithMD = markwon.toMarkdown(EmojiParser.parseToUnicode(dataModel.getDescription()));
CharSequence bodyWithMD = markwon.toMarkdown(EmojiParser.parseToUnicode(dataModel.getDescription()));
msDescription.setText(bodyWithMD);
}
else {
msDescription.setText("");
msDescription.setText(context.getString(R.string.milestoneNoDescription));
}
msOpenIssues.setText(String.valueOf(dataModel.getOpen_issues()));
msOpenIssues.setOnClickListener(new ClickListener(context.getResources().getString(R.string.milestoneOpenIssues, dataModel.getOpen_issues()), context));
msClosedIssues.setText(String.valueOf(dataModel.getClosed_issues()));
msClosedIssues.setOnClickListener(new ClickListener(context.getResources().getString(R.string.milestoneClosedIssues, dataModel.getClosed_issues()), context));
msOpenIssues.setText(context.getString(R.string.milestoneIssueStatusOpen, dataModel.getOpen_issues()));
msClosedIssues.setText(context.getString(R.string.milestoneIssueStatusClosed, dataModel.getClosed_issues()));
if((dataModel.getOpen_issues() + dataModel.getClosed_issues()) > 0) {
if(dataModel.getOpen_issues() == 0) {
msProgress.setProgress(100);
msProgress.setOnClickListener(new ClickListener(context.getResources().getString(R.string.milestoneCompletion, 100), context));
}
else {
int msCompletion = 100 * dataModel.getClosed_issues() / (dataModel.getOpen_issues() + dataModel.getClosed_issues());
msProgress.setOnClickListener(new ClickListener(context.getResources().getString(R.string.milestoneCompletion, msCompletion), context));
msProgress.setProgress(msCompletion);
}
}
else {
msProgress.setProgress(0);
msProgress.setOnClickListener(new ClickListener(context.getResources().getString(R.string.milestoneCompletion, 0), context));
}
if(dataModel.getDue_on() != null) {
@ -312,12 +281,14 @@ public class MilestonesAdapter extends RecyclerView.Adapter<RecyclerView.ViewHol
DateFormat formatter = new SimpleDateFormat("yyyy-MM-dd", new Locale(locale));
Date date = null;
try {
date = formatter.parse(dataModel.getDue_on());
}
catch(ParseException e) {
Log.e(TAG, e.toString());
}
assert date != null;
String dueDate = formatter.format(date);
@ -332,13 +303,16 @@ public class MilestonesAdapter extends RecyclerView.Adapter<RecyclerView.ViewHol
else if(timeFormat.equals("normal1")) {
SimpleDateFormat formatter = new SimpleDateFormat("dd-MM-yyyy", new Locale(locale));
Date date1 = null;
try {
date1 = formatter.parse(dataModel.getDue_on());
}
catch(ParseException e) {
Log.e(TAG, e.toString());
}
assert date1 != null;
String dueDate = formatter.format(date1);
msDueDate.setText(dueDate);
@ -347,7 +321,8 @@ public class MilestonesAdapter extends RecyclerView.Adapter<RecyclerView.ViewHol
}
else {
msDueDate.setText("");
msDueDate.setText(context.getString(R.string.milestoneNoDueDate));
}
}

View File

@ -11,14 +11,14 @@ import android.view.View;
import android.view.ViewGroup;
import android.widget.LinearLayout;
import android.widget.TextView;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.MultiSelectDialog;
import org.mian.gitnex.models.MultiSelectModel;
import java.util.ArrayList;
import androidx.annotation.NonNull;
import androidx.appcompat.widget.AppCompatCheckBox;
import androidx.core.content.ContextCompat;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.MultiSelectDialog;
import org.mian.gitnex.models.MultiSelectModel;
import java.util.List;
/**
* Author com.github.abumoallim, modified by M M Arif
@ -26,11 +26,11 @@ import androidx.recyclerview.widget.RecyclerView;
public class MutliSelectAdapter extends RecyclerView.Adapter<MutliSelectAdapter.MultiSelectDialogViewHolder> {
private ArrayList<MultiSelectModel> mDataSet;
private List<MultiSelectModel> mDataSet;
private String mSearchQuery = "";
private Context mContext;
public MutliSelectAdapter(ArrayList<MultiSelectModel> dataSet, Context context) {
public MutliSelectAdapter(List<MultiSelectModel> dataSet, Context context) {
this.mDataSet = dataSet;
this.mContext = context;
}
@ -163,7 +163,7 @@ public class MutliSelectAdapter extends RecyclerView.Adapter<MutliSelectAdapter.
return mDataSet.size();
}
public void setData(ArrayList<MultiSelectModel> data, String query, MutliSelectAdapter mutliSelectAdapter) {
public void setData(List<MultiSelectModel> data, String query, MutliSelectAdapter mutliSelectAdapter) {
this.mDataSet = data;
this.mSearchQuery = query;

View File

@ -1,6 +1,8 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.ClipData;
import android.content.ClipboardManager;
import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
@ -11,26 +13,31 @@ import android.widget.CheckBox;
import android.widget.Filter;
import android.widget.Filterable;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import com.amulyakhare.textdrawable.TextDrawable;
import com.amulyakhare.textdrawable.util.ColorGenerator;
import com.google.android.material.bottomsheet.BottomSheetDialog;
import org.mian.gitnex.R;
import org.mian.gitnex.activities.OpenRepoInBrowserActivity;
import org.mian.gitnex.activities.RepoDetailActivity;
import org.mian.gitnex.activities.RepoForksActivity;
import org.mian.gitnex.activities.RepoStargazersActivity;
import org.mian.gitnex.activities.RepoWatchersActivity;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.RepositoriesApi;
import org.mian.gitnex.database.models.Repository;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.UserRepositories;
import org.mian.gitnex.models.WatchInfo;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import java.util.Objects;
import retrofit2.Call;
import retrofit2.Callback;
@ -56,8 +63,12 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
private TextView repoOpenIssuesCount;
private TextView repoType;
private CheckBox isRepoAdmin;
private LinearLayout archiveRepo;
private TextView repoBranch;
private TextView htmlUrl;
private MyReposViewHolder(View itemView) {
super(itemView);
repoName = itemView.findViewById(R.id.repoName);
repoDescription = itemView.findViewById(R.id.repoDescription);
@ -70,6 +81,9 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
ImageView reposDropdownMenu = itemView.findViewById(R.id.reposDropdownMenu);
repoType = itemView.findViewById(R.id.repoType);
isRepoAdmin = itemView.findViewById(R.id.repoIsAdmin);
archiveRepo = itemView.findViewById(R.id.archiveRepoFrame);
repoBranch = itemView.findViewById(R.id.repoBranch);
htmlUrl = itemView.findViewById(R.id.htmlUrl);
itemView.setOnClickListener(v -> {
@ -83,13 +97,35 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
tinyDb.putString("repoType", repoType.getText().toString());
//tinyDb.putBoolean("resumeIssues", true);
tinyDb.putBoolean("isRepoAdmin", isRepoAdmin.isChecked());
tinyDb.putString("repoBranch", repoBranch.getText().toString());
//store if user is watching this repo
{
final String instanceUrl = tinyDb.getString("instanceUrl");
String[] parts = repoFullName.getText().toString().split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
int currentActiveAccountId = tinyDb.getInt("currentActiveAccountId");
RepositoriesApi repositoryData = new RepositoriesApi(context);
//RepositoriesRepository.deleteRepositoriesByAccount(currentActiveAccountId);
Integer count = repositoryData.checkRepository(currentActiveAccountId, repoOwner, repoName);
if(count == 0) {
long id = repositoryData.insertRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", id);
}
else {
Repository data = repositoryData.getRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", data.getRepositoryId());
}
//store if user is watching this repo
{
final String instanceUrl = tinyDb.getString("instanceUrl");
final String token = "token " + tinyDb.getString(tinyDb.getString("loginUid") + "-token");
WatchInfo watch = new WatchInfo();
@ -108,13 +144,14 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
assert response.body() != null;
tinyDb.putBoolean("repoWatch", response.body().getSubscribed());
} else {
}
else {
tinyDb.putBoolean("repoWatch", false);
if(response.code() != 404) {
Toasty.info(context, context.getString(R.string.genericApiStatusError));
Toasty.error(context, context.getString(R.string.genericApiStatusError));
}
@ -126,10 +163,11 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
public void onFailure(@NonNull Call<WatchInfo> call, @NonNull Throwable t) {
tinyDb.putBoolean("repoWatch", false);
Toasty.info(context, context.getString(R.string.genericApiStatusError));
Toasty.error(context, context.getString(R.string.genericApiStatusError));
}
});
}
context.startActivity(intent);
@ -140,19 +178,31 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
final Context context = v.getContext();
@SuppressLint("InflateParams")
View view = LayoutInflater.from(context).inflate(R.layout.bottom_sheet_repository_in_list, null);
@SuppressLint("InflateParams") View view = LayoutInflater.from(context).inflate(R.layout.bottom_sheet_repository_in_list, null);
TextView repoOpenInBrowser = view.findViewById(R.id.repoOpenInBrowser);
TextView repoStargazers = view.findViewById(R.id.repoStargazers);
TextView repoWatchers = view.findViewById(R.id.repoWatchers);
TextView repoForksList = view.findViewById(R.id.repoForksList);
TextView repoCopyUrl = view.findViewById(R.id.repoCopyUrl);
TextView bottomSheetHeader = view.findViewById(R.id.bottomSheetHeader);
bottomSheetHeader.setText(repoFullName.getText());
bottomSheetHeader.setText(String.format("%s / %s", repoFullName.getText().toString().split("/")[0], repoFullName.getText().toString().split("/")[1]));
BottomSheetDialog dialog = new BottomSheetDialog(context);
dialog.setContentView(view);
dialog.show();
repoCopyUrl.setOnClickListener(openInBrowser -> {
ClipboardManager clipboard = (ClipboardManager) Objects.requireNonNull(context).getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText("repoUrl", htmlUrl.getText().toString());
assert clipboard != null;
clipboard.setPrimaryClip(clip);
Toasty.info(context, context.getString(R.string.copyIssueUrlToastMsg));
dialog.dismiss();
});
repoOpenInBrowser.setOnClickListener(openInBrowser -> {
Intent intentOpenInBrowser = new Intent(context, OpenRepoInBrowserActivity.class);
@ -180,12 +230,23 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
});
repoForksList.setOnClickListener(forks -> {
Intent intentW = new Intent(context, RepoForksActivity.class);
intentW.putExtra("repoFullNameForForks", repoFullName.getText());
context.startActivity(intentW);
dialog.dismiss();
});
});
}
}
public MyReposListAdapter(Context mCtx, List<UserRepositories> reposListMain) {
this.mCtx = mCtx;
this.reposList = reposListMain;
reposListFull = new ArrayList<>(reposList);
@ -194,6 +255,7 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
@NonNull
@Override
public MyReposListAdapter.MyReposViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_repositories, parent, false);
return new MyReposListAdapter.MyReposViewHolder(v);
}
@ -203,25 +265,20 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
UserRepositories currentItem = reposList.get(position);
holder.repoDescription.setVisibility(View.GONE);
holder.repoBranch.setText(currentItem.getDefault_branch());
holder.htmlUrl.setText(currentItem.getHtml_url());
ColorGenerator generator = ColorGenerator.MATERIAL;
int color = generator.getColor(currentItem.getName());
String firstCharacter = String.valueOf(currentItem.getName().charAt(0));
TextDrawable drawable = TextDrawable.builder()
.beginConfig()
.useFont(Typeface.DEFAULT)
.fontSize(18)
.toUpperCase()
.width(28)
.height(28)
.endConfig()
.buildRoundRect(firstCharacter, color, 3);
TextDrawable drawable = TextDrawable.builder().beginConfig().useFont(Typeface.DEFAULT).fontSize(18).toUpperCase().width(28).height(28).endConfig().buildRoundRect(firstCharacter, color, 3);
if(currentItem.getAvatar_url() != null) {
if(!currentItem.getAvatar_url().equals("")) {
PicassoService.getInstance(mCtx).get().load(currentItem.getAvatar_url()).placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(120, 120).centerCrop().into(holder.imageAvatar);
} else {
}
else {
holder.imageAvatar.setImageDrawable(drawable);
}
}
@ -234,13 +291,13 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
holder.repoDescription.setVisibility(View.VISIBLE);
holder.repoDescription.setText(currentItem.getDescription());
}
holder.repoFullName.setText(currentItem.getFullname());
holder.repoFullName.setText(currentItem.getFullName());
if(currentItem.getPrivateFlag()) {
holder.repoPrivatePublic.setImageResource(R.drawable.ic_lock_bold);
holder.repoPrivatePublic.setImageResource(R.drawable.ic_lock);
holder.repoType.setText(R.string.strPrivate);
}
else {
holder.repoPrivatePublic.setImageResource(R.drawable.ic_public);
holder.repoPrivatePublic.setVisibility(View.GONE);
holder.repoType.setText(R.string.strPublic);
}
holder.repoStars.setText(currentItem.getStars_count());
@ -252,30 +309,42 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
}
holder.isRepoAdmin.setChecked(currentItem.getPermissions().isAdmin());
if(currentItem.isArchived()) {
holder.archiveRepo.setVisibility(View.VISIBLE);
}
else {
holder.archiveRepo.setVisibility(View.GONE);
}
}
@Override
public int getItemCount() {
return reposList.size();
}
@Override
public Filter getFilter() {
return myReposFilter;
}
private Filter myReposFilter = new Filter() {
@Override
protected FilterResults performFiltering(CharSequence constraint) {
List<UserRepositories> filteredList = new ArrayList<>();
if(constraint == null || constraint.length() == 0) {
filteredList.addAll(reposListFull);
} else {
}
else {
String filterPattern = constraint.toString().toLowerCase().trim();
for(UserRepositories item : reposListFull) {
if (item.getFullname().toLowerCase().contains(filterPattern) || item.getDescription().toLowerCase().contains(filterPattern)) {
if(item.getFullName().toLowerCase().contains(filterPattern) || item.getDescription().toLowerCase().contains(filterPattern)) {
filteredList.add(item);
}
}
@ -289,9 +358,11 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
@Override
protected void publishResults(CharSequence constraint, FilterResults results) {
reposList.clear();
reposList.addAll((List) results.values);
notifyDataSetChanged();
}
};
}

View File

@ -0,0 +1,166 @@
package org.mian.gitnex.adapters;
import android.content.Context;
import android.text.Html;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.database.api.RepositoriesApi;
import org.mian.gitnex.database.models.Repository;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.NotificationThread;
import java.util.List;
/**
* Author opyale
*/
public class NotificationsAdapter extends RecyclerView.Adapter<NotificationsAdapter.NotificationsViewHolder> {
private Context context;
private List<NotificationThread> notificationThreads;
private OnMoreClickedListener onMoreClickedListener;
private OnNotificationClickedListener onNotificationClickedListener;
private TinyDB tinyDb;
public NotificationsAdapter(Context context, List<NotificationThread> notificationThreads, OnMoreClickedListener onMoreClickedListener, OnNotificationClickedListener onNotificationClickedListener) {
this.tinyDb = new TinyDB(context);
this.context = context;
this.notificationThreads = notificationThreads;
this.onMoreClickedListener = onMoreClickedListener;
this.onNotificationClickedListener = onNotificationClickedListener;
}
static class NotificationsViewHolder extends RecyclerView.ViewHolder {
private LinearLayout frame;
private TextView subject;
private TextView repository;
private ImageView typePr;
private ImageView typeIssue;
private ImageView typeUnknown;
private ImageView pinned;
private ImageView more;
public NotificationsViewHolder(@NonNull View itemView) {
super(itemView);
frame = itemView.findViewById(R.id.frame);
subject = itemView.findViewById(R.id.subject);
repository = itemView.findViewById(R.id.repository);
typePr = itemView.findViewById(R.id.typePr);
typeIssue = itemView.findViewById(R.id.typeIssue);
typeUnknown = itemView.findViewById(R.id.typeUnknown);
pinned = itemView.findViewById(R.id.pinned);
more = itemView.findViewById(R.id.more);
}
}
@NonNull
@Override
public NotificationsViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View v = LayoutInflater.from(context).inflate(R.layout.list_notifications, parent, false);
return new NotificationsAdapter.NotificationsViewHolder(v);
}
@Override
public void onBindViewHolder(@NonNull NotificationsViewHolder holder, int position) {
NotificationThread notificationThread = notificationThreads.get(position);
String url = notificationThread.getSubject().getUrl();
String subjectId = "<font color='" + context.getResources().getColor(R.color.lightGray) + "'>" + context.getResources()
.getString(R.string.hash) + url.substring(url.lastIndexOf("/") + 1) + "</font>";
holder.subject.setText(Html.fromHtml(subjectId + " " + notificationThread.getSubject().getTitle()));
holder.repository.setText(notificationThread.getRepository().getFullName());
if(notificationThread.isPinned()) {
holder.pinned.setVisibility(View.VISIBLE);
}
else {
holder.pinned.setVisibility(View.GONE);
}
switch(notificationThread.getSubject().getType()) {
case "Pull":
holder.typePr.setVisibility(View.VISIBLE);
holder.typeIssue.setVisibility(View.GONE);
holder.typeUnknown.setVisibility(View.GONE);
break;
case "Issue":
holder.typePr.setVisibility(View.GONE);
holder.typeIssue.setVisibility(View.VISIBLE);
holder.typeUnknown.setVisibility(View.GONE);
break;
default:
holder.typePr.setVisibility(View.GONE);
holder.typeIssue.setVisibility(View.GONE);
holder.typeUnknown.setVisibility(View.VISIBLE);
break;
}
holder.frame.setOnClickListener(v -> {
onNotificationClickedListener.onNotificationClicked(notificationThread);
String[] parts = notificationThread.getRepository().getFullName().split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
int currentActiveAccountId = tinyDb.getInt("currentActiveAccountId");
RepositoriesApi repositoryData = new RepositoriesApi(context);
Integer count = repositoryData.checkRepository(currentActiveAccountId, repoOwner, repoName);
if(count == 0) {
long id = repositoryData.insertRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", id);
}
else {
Repository data = repositoryData.getRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", data.getRepositoryId());
}
});
holder.more.setOnClickListener(v -> onMoreClickedListener.onMoreClicked(notificationThread));
}
@Override
public int getItemCount() {
return notificationThreads.size();
}
public interface OnNotificationClickedListener {
void onNotificationClicked(NotificationThread notificationThread);
}
public interface OnMoreClickedListener {
void onMoreClicked(NotificationThread notificationThread);
}
}

View File

@ -1,7 +1,5 @@
package org.mian.gitnex.adapters;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import android.annotation.SuppressLint;
import android.content.Context;
import android.content.Intent;
@ -12,12 +10,14 @@ import android.widget.Filter;
import android.widget.Filterable;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.activities.OrganizationDetailActivity;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.models.UserOrganizations;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.UserOrganizations;
import java.util.ArrayList;
import java.util.List;

View File

@ -58,7 +58,7 @@ public class ProfileEmailsAdapter extends RecyclerView.Adapter<ProfileEmailsAdap
if(currentItem.getPrimary()) {
TextDrawable drawable = TextDrawable.builder()
.beginConfig()
.textColor(mCtx.getResources().getColor(R.color.white))
.textColor(mCtx.getResources().getColor(R.color.colorWhite))
.fontSize(36)
.width(220)
.height(60)

View File

@ -18,8 +18,8 @@ import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.helpers.ClickListener;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TimeHelper;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.PullRequests;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
import java.util.Locale;
@ -136,7 +136,7 @@ public class PullRequestsAdapter extends RecyclerView.Adapter<RecyclerView.ViewH
tinyDb.putString("prHeadBranch", prHeadBranch.getText().toString());
tinyDb.putString("prIsFork", prIsFork.getText().toString());
tinyDb.putString("prForkFullName", prForkFullName.getText().toString());
tinyDb.putString("issueType", "pr");
tinyDb.putString("issueType", "Pull");
context.startActivity(intent);
});
@ -155,7 +155,7 @@ public class PullRequestsAdapter extends RecyclerView.Adapter<RecyclerView.ViewH
tinyDb.putString("prHeadBranch", prHeadBranch.getText().toString());
tinyDb.putString("prIsFork", prIsFork.getText().toString());
tinyDb.putString("prForkFullName", prForkFullName.getText().toString());
tinyDb.putString("issueType", "pr");
tinyDb.putString("issueType", "Pull");
context.startActivity(intent);
});
@ -188,9 +188,18 @@ public class PullRequestsAdapter extends RecyclerView.Adapter<RecyclerView.ViewH
prNumber.setText(String.valueOf(prModel.getNumber()));
prMergeable.setText(String.valueOf(prModel.isMergeable()));
if(prModel.getHead() != null) {
prHeadBranch.setText(prModel.getHead().getRef());
if(prModel.getHead().getRepo() != null) {
prIsFork.setText(String.valueOf(prModel.getHead().getRepo().isFork()));
prForkFullName.setText(prModel.getHead().getRepo().getFull_name());
}
else {
// pull was done from a deleted fork
prIsFork.setText("true");
prForkFullName.setText(context.getString(R.string.prDeletedFrok));
}
}
prCommentsCount.setText(String.valueOf(prModel.getComments()));
prCreatedTime.setText(TimeHelper.formatTime(prModel.getCreated_at(), new Locale(locale), timeFormat, context));

View File

@ -10,19 +10,25 @@ import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.RelativeLayout;
import android.widget.TextView;
import com.amulyakhare.textdrawable.TextDrawable;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
import com.vdurmont.emoji.EmojiParser;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.helpers.ClickListener;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TimeHelper;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.Releases;
import org.mian.gitnex.util.TinyDB;
import java.util.Collection;
import java.util.Collections;
import java.util.List;
import java.util.Locale;
import java.util.Objects;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.recyclerview.widget.RecyclerView;
import io.noties.markwon.AbstractMarkwonPlugin;
import io.noties.markwon.Markwon;
import io.noties.markwon.core.CorePlugin;
@ -31,7 +37,6 @@ import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.ext.tables.TablePlugin;
import io.noties.markwon.ext.tasklist.TaskListPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.image.AsyncDrawable;
import io.noties.markwon.image.DefaultMediaDecoder;
import io.noties.markwon.image.ImageItem;
import io.noties.markwon.image.ImagesPlugin;
@ -51,23 +56,42 @@ public class ReleasesAdapter extends RecyclerView.Adapter<ReleasesAdapter.Releas
static class ReleasesViewHolder extends RecyclerView.ViewHolder {
private ImageView releaseType;
private TextView releaseTitle;
private TextView releaseDescription;
private TextView releaseDownload;
private TextView releaseType;
private TextView releaseName;
private ImageView authorAvatar;
private TextView authorName;
private TextView releaseTag;
private TextView releaseCommitSha;
private TextView releaseDate;
private TextView releaseBodyContent;
private LinearLayout downloadFrame;
private RelativeLayout downloads;
private TextView releaseZipDownload;
private TextView releaseTarDownload;
private TextView releaseTag;
private ImageView downloadDropdownIcon;
private RecyclerView downloadList;
private ReleasesViewHolder(View itemView) {
super(itemView);
releaseType = itemView.findViewById(R.id.releaseType);
releaseTitle = itemView.findViewById(R.id.releaseTitle);
releaseDescription = itemView.findViewById(R.id.releaseDescription);
releaseName = itemView.findViewById(R.id.releaseName);
authorAvatar = itemView.findViewById(R.id.authorAvatar);
authorName = itemView.findViewById(R.id.authorName);
releaseTag = itemView.findViewById(R.id.releaseTag);
releaseCommitSha = itemView.findViewById(R.id.releaseCommitSha);
releaseDate = itemView.findViewById(R.id.releaseDate);
releaseBodyContent = itemView.findViewById(R.id.releaseBodyContent);
downloadFrame = itemView.findViewById(R.id.downloadFrame);
downloads = itemView.findViewById(R.id.downloads);
releaseZipDownload = itemView.findViewById(R.id.releaseZipDownload);
releaseTarDownload = itemView.findViewById(R.id.releaseTarDownload);
releaseTag = itemView.findViewById(R.id.releaseTag);
downloadDropdownIcon = itemView.findViewById(R.id.downloadDropdownIcon);
downloadList = itemView.findViewById(R.id.downloadList);
downloadList.setHasFixedSize(true);
downloadList.setLayoutManager(new LinearLayoutManager(itemView.getContext()));
}
}
@ -88,48 +112,46 @@ public class ReleasesAdapter extends RecyclerView.Adapter<ReleasesAdapter.Releas
public void onBindViewHolder(@NonNull ReleasesAdapter.ReleasesViewHolder holder, int position) {
final TinyDB tinyDb = new TinyDB(mCtx);
final String locale = tinyDb.getString("locale");
final String timeFormat = tinyDb.getString("dateFormat");
Releases currentItem = releasesList.get(position);
holder.releaseTitle.setText(currentItem.getName());
if(!currentItem.getTag_name().equals("")) {
holder.releaseTag.setText(mCtx.getResources().getString(R.string.releaseTag, currentItem.getTag_name()));
}
else {
holder.releaseTag.setVisibility(View.GONE);
}
holder.releaseName.setText(currentItem.getName());
if(currentItem.isPrerelease()) {
TextDrawable drawable = TextDrawable.builder()
.beginConfig()
//.useFont(Typeface.DEFAULT)
.textColor(mCtx.getResources().getColor(R.color.white))
.fontSize(34)
.width(260)
.height(60)
.endConfig()
.buildRoundRect(mCtx.getResources().getString(R.string.releaseTypePre), mCtx.getResources().getColor(R.color.releasePre), 8);
holder.releaseType.setImageDrawable(drawable);
holder.releaseType.setBackgroundResource(R.drawable.shape_pre_release);
holder.releaseType.setText(R.string.releaseTypePre);
}
else if(currentItem.isDraft()) {
holder.releaseType.setVisibility(View.GONE);
}
else {
TextDrawable drawable = TextDrawable.builder()
.beginConfig()
//.useFont(Typeface.DEFAULT)
.textColor(mCtx.getResources().getColor(R.color.white))
.fontSize(34)
.width(260)
.height(60)
.endConfig()
.buildRoundRect(mCtx.getResources().getString(R.string.releaseTypeStable), mCtx.getResources().getColor(R.color.releaseStable), 8);
holder.releaseType.setImageDrawable(drawable);
holder.releaseType.setBackgroundResource(R.drawable.shape_stable_release);
holder.releaseType.setText(R.string.releaseTypeStable);
}
if(currentItem.getAuthor().getAvatar_url() != null) {
PicassoService.getInstance(mCtx).get().load(currentItem.getAuthor().getAvatar_url()).placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(120, 120).centerCrop().into(holder.authorAvatar);
}
holder.authorName.setText(mCtx.getResources().getString(R.string.releasePublishedBy, currentItem.getAuthor().getUsername()));
if(currentItem.getTag_name() != null) {
holder.releaseTag.setText(currentItem.getTag_name());
}
if(currentItem.getPublished_at() != null) {
holder.releaseDate.setText(TimeHelper.formatTime(currentItem.getPublished_at(), new Locale(locale), timeFormat, mCtx));
}
if(timeFormat.equals("pretty")) {
holder.releaseDate.setOnClickListener(new ClickListener(TimeHelper.customDateFormatForToastDateFormat(currentItem.getPublished_at()), mCtx));
}
final Markwon markwon = Markwon.builder(Objects.requireNonNull(mCtx))
.usePlugin(CorePlugin.create())
.usePlugin(ImagesPlugin.create(new ImagesPlugin.ImagesConfigure() {
@Override
public void configureImages(@NonNull ImagesPlugin plugin) {
.usePlugin(ImagesPlugin.create(plugin -> {
plugin.addSchemeHandler(new SchemeHandler() {
@NonNull
@Override
@ -152,19 +174,12 @@ public class ReleasesAdapter extends RecyclerView.Adapter<ReleasesAdapter.Releas
return Collections.singleton("drawable");
}
});
plugin.placeholderProvider(new ImagesPlugin.PlaceholderProvider() {
@Nullable
@Override
public Drawable providePlaceholder(@NonNull AsyncDrawable drawable) {
return null;
}
});
plugin.placeholderProvider(drawable -> null);
plugin.addMediaDecoder(GifMediaDecoder.create(false));
plugin.addMediaDecoder(SvgMediaDecoder.create(mCtx.getResources()));
plugin.addMediaDecoder(SvgMediaDecoder.create());
plugin.defaultMediaDecoder(DefaultMediaDecoder.create(mCtx.getResources()));
plugin.defaultMediaDecoder(DefaultMediaDecoder.create());
}
}))
.usePlugin(new AbstractMarkwonPlugin() {
@Override
@ -185,12 +200,29 @@ public class ReleasesAdapter extends RecyclerView.Adapter<ReleasesAdapter.Releas
Spanned bodyWithMD = markwon.toMarkdown(EmojiParser.parseToUnicode(currentItem.getBody()));
if(!currentItem.getBody().equals("")) {
markwon.setParsedMarkdown(holder.releaseDescription, bodyWithMD);
markwon.setParsedMarkdown(holder.releaseBodyContent, bodyWithMD);
}
else {
holder.releaseDescription.setVisibility(View.GONE);
holder.releaseBodyContent.setText(R.string.noReleaseBodyContent);
}
holder.downloadFrame.setOnClickListener(v -> {
if(holder.downloads.getVisibility() == View.GONE) {
holder.downloadDropdownIcon.setImageResource(R.drawable.ic_chevron_down);
holder.downloads.setVisibility(View.VISIBLE);
}
else {
holder.downloadDropdownIcon.setImageResource(R.drawable.ic_chevron_right);
holder.downloads.setVisibility(View.GONE);
}
});
holder.releaseZipDownload.setText(
Html.fromHtml("<a href='" + currentItem.getZipball_url() + "'>" + mCtx.getResources().getString(R.string.zipArchiveDownloadReleasesTab) + "</a> "));
holder.releaseZipDownload.setMovementMethod(LinkMovementMethod.getInstance());
@ -199,6 +231,9 @@ public class ReleasesAdapter extends RecyclerView.Adapter<ReleasesAdapter.Releas
Html.fromHtml("<a href='" + currentItem.getTarball_url() + "'>" + mCtx.getResources().getString(R.string.tarArchiveDownloadReleasesTab) + "</a> "));
holder.releaseTarDownload.setMovementMethod(LinkMovementMethod.getInstance());
ReleasesDownloadsAdapter adapter = new ReleasesDownloadsAdapter(currentItem.getAssets());
holder.downloadList.setAdapter(adapter);
}
@Override

View File

@ -0,0 +1,68 @@
package org.mian.gitnex.adapters;
import android.text.Html;
import android.text.method.LinkMovementMethod;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.models.Releases;
import java.util.List;
/**
* Author M M Arif
**/
public class ReleasesDownloadsAdapter extends RecyclerView.Adapter<ReleasesDownloadsAdapter.ReleasesDownloadsViewHolder> {
private List<Releases.assetsObject> releasesDownloadsList;
static class ReleasesDownloadsViewHolder extends RecyclerView.ViewHolder {
private TextView downloadName;
private ReleasesDownloadsViewHolder(View itemView) {
super(itemView);
downloadName = itemView.findViewById(R.id.downloadName);
}
}
ReleasesDownloadsAdapter(List<Releases.assetsObject> releasesDownloadsMain) {
this.releasesDownloadsList = releasesDownloadsMain;
}
@NonNull
@Override
public ReleasesDownloadsAdapter.ReleasesDownloadsViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_releases_downloads, parent, false);
return new ReleasesDownloadsAdapter.ReleasesDownloadsViewHolder(v);
}
@Override
public void onBindViewHolder(@NonNull ReleasesDownloadsAdapter.ReleasesDownloadsViewHolder holder, int position) {
Releases.assetsObject currentItem = releasesDownloadsList.get(position);
if(currentItem.getName() != null) {
holder.downloadName.setText(
Html.fromHtml("<a href='" + currentItem.getBrowser_download_url() + "'>" + currentItem.getName() + "</a> "));
holder.downloadName.setMovementMethod(LinkMovementMethod.getInstance());
}
}
@Override
public int getItemCount() {
return releasesDownloadsList.size();
}
}

View File

@ -0,0 +1,396 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.CheckBox;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import com.amulyakhare.textdrawable.TextDrawable;
import com.amulyakhare.textdrawable.util.ColorGenerator;
import com.google.android.material.bottomsheet.BottomSheetDialog;
import org.mian.gitnex.R;
import org.mian.gitnex.activities.OpenRepoInBrowserActivity;
import org.mian.gitnex.activities.RepoDetailActivity;
import org.mian.gitnex.activities.RepoForksActivity;
import org.mian.gitnex.activities.RepoStargazersActivity;
import org.mian.gitnex.activities.RepoWatchersActivity;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.RepositoriesApi;
import org.mian.gitnex.database.models.Repository;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.UserRepositories;
import org.mian.gitnex.models.WatchInfo;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
/**
* Author M M Arif
*/
public class RepoForksAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
private Context ctx;
private final int TYPE_LOAD = 0;
private List<UserRepositories> forksList;
private OnLoadMoreListener loadMoreListener;
private boolean isLoading = false;
private boolean isMoreDataAvailable = true;
public RepoForksAdapter(Context ctx, List<UserRepositories> forksListMain) {
this.ctx = ctx;
this.forksList = forksListMain;
}
@NonNull
@Override
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
LayoutInflater inflater = LayoutInflater.from(ctx);
if(viewType == TYPE_LOAD) {
return new RepoForksAdapter.ForksHolder(inflater.inflate(R.layout.list_repositories, parent, false));
}
else {
return new LoadHolder(inflater.inflate(R.layout.row_load, parent, false));
}
}
@Override
public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int position) {
if(position >= getItemCount() - 1 && isMoreDataAvailable && !isLoading && loadMoreListener != null) {
isLoading = true;
loadMoreListener.onLoadMore();
}
if(getItemViewType(position) == TYPE_LOAD) {
((RepoForksAdapter.ForksHolder) holder).bindData(forksList.get(position));
}
}
@Override
public int getItemViewType(int position) {
if(forksList.get(position).getName() != null) {
return TYPE_LOAD;
}
else {
return 1;
}
}
@Override
public int getItemCount() {
return forksList.size();
}
class ForksHolder extends RecyclerView.ViewHolder {
private ImageView image;
private TextView repoName;
private TextView repoDescription;
private TextView fullName;
private CheckBox isRepoAdmin;
private ImageView repoPrivatePublic;
private TextView repoStars;
private TextView repoForks;
private TextView repoOpenIssuesCount;
private TextView repoType;
private LinearLayout archiveRepo;
private TextView repoBranch;
private ImageView reposDropdownMenu;
ForksHolder(View itemView) {
super(itemView);
repoName = itemView.findViewById(R.id.repoName);
repoDescription = itemView.findViewById(R.id.repoDescription);
isRepoAdmin = itemView.findViewById(R.id.repoIsAdmin);
image = itemView.findViewById(R.id.imageAvatar);
fullName = itemView.findViewById(R.id.repoFullName);
repoPrivatePublic = itemView.findViewById(R.id.imageRepoType);
repoStars = itemView.findViewById(R.id.repoStars);
repoForks = itemView.findViewById(R.id.repoForks);
repoOpenIssuesCount = itemView.findViewById(R.id.repoOpenIssuesCount);
reposDropdownMenu = itemView.findViewById(R.id.reposDropdownMenu);
repoType = itemView.findViewById(R.id.repoType);
archiveRepo = itemView.findViewById(R.id.archiveRepoFrame);
repoBranch = itemView.findViewById(R.id.repoBranch);
}
@SuppressLint("SetTextI18n")
void bindData(UserRepositories forksModel) {
repoDescription.setVisibility(View.GONE);
repoBranch.setText(forksModel.getDefault_branch());
ColorGenerator generator = ColorGenerator.MATERIAL;
int color = generator.getColor(forksModel.getName());
String firstCharacter = String.valueOf(forksModel.getName().charAt(0));
TextDrawable drawable = TextDrawable.builder().beginConfig().useFont(Typeface.DEFAULT).fontSize(18).toUpperCase().width(28).height(28)
.endConfig().buildRoundRect(firstCharacter, color, 3);
if(forksModel.getAvatar_url() != null) {
if(!forksModel.getAvatar_url().equals("")) {
PicassoService.getInstance(ctx).get().load(forksModel.getAvatar_url()).placeholder(R.drawable.loader_animated)
.transform(new RoundedTransformation(8, 0)).resize(120, 120).centerCrop().into(image);
}
else {
image.setImageDrawable(drawable);
}
}
else {
image.setImageDrawable(drawable);
}
repoName.setText(forksModel.getName());
if(!forksModel.getDescription().equals("")) {
repoDescription.setVisibility(View.VISIBLE);
repoDescription.setText(forksModel.getDescription());
}
fullName.setText(forksModel.getFullName());
if(forksModel.getPrivateFlag()) {
repoPrivatePublic.setImageResource(R.drawable.ic_lock);
repoType.setText(R.string.strPrivate);
}
else {
repoPrivatePublic.setVisibility(View.GONE);
repoType.setText(R.string.strPublic);
}
repoStars.setText(forksModel.getStars_count());
repoForks.setText(forksModel.getForks_count());
repoOpenIssuesCount.setText(forksModel.getOpen_issues_count());
if(isRepoAdmin == null) {
isRepoAdmin = new CheckBox(ctx);
}
isRepoAdmin.setChecked(forksModel.getPermissions().isAdmin());
if(forksModel.isArchived()) {
archiveRepo.setVisibility(View.VISIBLE);
}
else {
archiveRepo.setVisibility(View.GONE);
}
itemView.setOnClickListener(v -> {
Context context = v.getContext();
TextView repoFullName = v.findViewById(R.id.repoFullName);
TextView repoType_ = v.findViewById(R.id.repoType);
Intent intent = new Intent(context, RepoDetailActivity.class);
intent.putExtra("repoFullName", repoFullName.getText().toString());
TinyDB tinyDb = new TinyDB(context);
tinyDb.putString("repoFullName", repoFullName.getText().toString());
tinyDb.putString("repoType", repoType_.getText().toString());
//tinyDb.putBoolean("resumeIssues", true);
tinyDb.putBoolean("isRepoAdmin", isRepoAdmin.isChecked());
tinyDb.putString("repoBranch", repoBranch.getText().toString());
String[] parts = repoFullName.getText().toString().split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
int currentActiveAccountId = tinyDb.getInt("currentActiveAccountId");
RepositoriesApi repositoryData = new RepositoriesApi(context);
//RepositoriesRepository.deleteRepositoriesByAccount(currentActiveAccountId);
Integer count = repositoryData.checkRepository(currentActiveAccountId, repoOwner, repoName);
if(count == 0) {
long id = repositoryData.insertRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", id);
}
else {
Repository data = repositoryData.getRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", data.getRepositoryId());
}
//store if user is watching this repo
{
final String instanceUrl = tinyDb.getString("instanceUrl");
final String token = "token " + tinyDb.getString(tinyDb.getString("loginUid") + "-token");
WatchInfo watch = new WatchInfo();
Call<WatchInfo> call;
call = RetrofitClient.getInstance(instanceUrl, context).getApiInterface().checkRepoWatchStatus(token, repoOwner, repoName);
call.enqueue(new Callback<WatchInfo>() {
@Override
public void onResponse(@NonNull Call<WatchInfo> call, @NonNull retrofit2.Response<WatchInfo> response) {
if(response.isSuccessful()) {
assert response.body() != null;
tinyDb.putBoolean("repoWatch", response.body().getSubscribed());
}
else {
tinyDb.putBoolean("repoWatch", false);
if(response.code() != 404) {
Toasty.error(context, context.getString(R.string.genericApiStatusError));
}
}
}
@Override
public void onFailure(@NonNull Call<WatchInfo> call, @NonNull Throwable t) {
tinyDb.putBoolean("repoWatch", false);
Toasty.error(context, context.getString(R.string.genericApiStatusError));
}
});
}
context.startActivity(intent);
});
reposDropdownMenu.setOnClickListener(v -> {
final Context context = v.getContext();
@SuppressLint("InflateParams") View view = LayoutInflater.from(context).inflate(R.layout.bottom_sheet_repository_in_list, null);
TextView repoOpenInBrowser = view.findViewById(R.id.repoOpenInBrowser);
TextView repoStargazers = view.findViewById(R.id.repoStargazers);
TextView repoWatchers = view.findViewById(R.id.repoWatchers);
TextView repoForksList = view.findViewById(R.id.repoForksList);
TextView bottomSheetHeader = view.findViewById(R.id.bottomSheetHeader);
bottomSheetHeader
.setText(String.format("%s / %s", fullName.getText().toString().split("/")[0], fullName.getText().toString().split("/")[1]));
BottomSheetDialog dialog = new BottomSheetDialog(context);
dialog.setContentView(view);
dialog.show();
repoOpenInBrowser.setOnClickListener(openInBrowser -> {
Intent intentOpenInBrowser = new Intent(context, OpenRepoInBrowserActivity.class);
intentOpenInBrowser.putExtra("repoFullNameBrowser", fullName.getText());
context.startActivity(intentOpenInBrowser);
dialog.dismiss();
});
repoStargazers.setOnClickListener(stargazers -> {
Intent intent = new Intent(context, RepoStargazersActivity.class);
intent.putExtra("repoFullNameForStars", fullName.getText());
context.startActivity(intent);
dialog.dismiss();
});
repoWatchers.setOnClickListener(watchers -> {
Intent intentW = new Intent(context, RepoWatchersActivity.class);
intentW.putExtra("repoFullNameForWatchers", fullName.getText());
context.startActivity(intentW);
dialog.dismiss();
});
repoForksList.setOnClickListener(watchers -> {
Intent intentW = new Intent(context, RepoForksActivity.class);
intentW.putExtra("repoFullNameForForks", fullName.getText());
context.startActivity(intentW);
dialog.dismiss();
});
});
}
}
static class LoadHolder extends RecyclerView.ViewHolder {
LoadHolder(View itemView) {
super(itemView);
}
}
public void setMoreDataAvailable(boolean moreDataAvailable) {
isMoreDataAvailable = moreDataAvailable;
}
public void notifyDataChanged() {
notifyDataSetChanged();
isLoading = false;
}
public interface OnLoadMoreListener {
void onLoadMore();
}
public void setLoadMoreListener(RepoForksAdapter.OnLoadMoreListener loadMoreListener) {
this.loadMoreListener = loadMoreListener;
}
public void updateList(List<UserRepositories> list) {
forksList = list;
notifyDataSetChanged();
}
}

View File

@ -12,8 +12,8 @@ import android.widget.TextView;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
/**
@ -109,13 +109,6 @@ public class RepoStargazersAdapter extends BaseAdapter {
viewHolder.memberName.setTypeface(myTypeface);
}
if(tinyDb.getInt("themeId") == 1) { //light
viewHolder.memberName.setTextColor(mCtx.getResources().getColor(R.color.lightThemeTextColor));
}
else { // dark
viewHolder.memberName.setTextColor(mCtx.getResources().getColor(R.color.white));
}
}
}

View File

@ -12,8 +12,8 @@ import android.widget.TextView;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
/**
@ -109,13 +109,6 @@ public class RepoWatchersAdapter extends BaseAdapter {
viewHolder.memberName.setTypeface(myTypeface);
}
if(tinyDb.getInt("themeId") == 1) { //light
viewHolder.memberName.setTextColor(mCtx.getResources().getColor(R.color.lightThemeTextColor));
}
else { // dark
viewHolder.memberName.setTextColor(mCtx.getResources().getColor(R.color.white));
}
}
}

View File

@ -1,6 +1,8 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.ClipData;
import android.content.ClipboardManager;
import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
@ -11,6 +13,7 @@ import android.widget.CheckBox;
import android.widget.Filter;
import android.widget.Filterable;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
@ -22,15 +25,19 @@ import org.mian.gitnex.activities.OpenRepoInBrowserActivity;
import org.mian.gitnex.activities.RepoDetailActivity;
import org.mian.gitnex.activities.RepoStargazersActivity;
import org.mian.gitnex.activities.RepoWatchersActivity;
import org.mian.gitnex.activities.RepoForksActivity;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.RepositoriesApi;
import org.mian.gitnex.database.models.Repository;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.UserRepositories;
import org.mian.gitnex.models.WatchInfo;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import java.util.Objects;
import retrofit2.Call;
import retrofit2.Callback;
@ -56,6 +63,9 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
private TextView repoForks;
private TextView repoOpenIssuesCount;
private TextView repoType;
private LinearLayout archiveRepo;
private TextView repoBranch;
private TextView htmlUrl;
private ReposViewHolder(View itemView) {
@ -71,6 +81,9 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
repoOpenIssuesCount = itemView.findViewById(R.id.repoOpenIssuesCount);
ImageView reposDropdownMenu = itemView.findViewById(R.id.reposDropdownMenu);
repoType = itemView.findViewById(R.id.repoType);
archiveRepo = itemView.findViewById(R.id.archiveRepoFrame);
repoBranch = itemView.findViewById(R.id.repoBranch);
htmlUrl = itemView.findViewById(R.id.htmlUrl);
itemView.setOnClickListener(v -> {
@ -86,13 +99,35 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
tinyDb.putString("repoType", repoType_.getText().toString());
//tinyDb.putBoolean("resumeIssues", true);
tinyDb.putBoolean("isRepoAdmin", isRepoAdmin.isChecked());
tinyDb.putString("repoBranch", repoBranch.getText().toString());
//store if user is watching this repo
{
final String instanceUrl = tinyDb.getString("instanceUrl");
String[] parts = repoFullName.getText().toString().split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
int currentActiveAccountId = tinyDb.getInt("currentActiveAccountId");
RepositoriesApi repositoryData = new RepositoriesApi(context);
//RepositoriesRepository.deleteRepositoriesByAccount(currentActiveAccountId);
Integer count = repositoryData.checkRepository(currentActiveAccountId, repoOwner, repoName);
if(count == 0) {
long id = repositoryData.insertRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", id);
}
else {
Repository data = repositoryData.getRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", data.getRepositoryId());
}
//store if user is watching this repo
{
final String instanceUrl = tinyDb.getString("instanceUrl");
final String token = "token " + tinyDb.getString(tinyDb.getString("loginUid") + "-token");
WatchInfo watch = new WatchInfo();
@ -117,7 +152,7 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
if(response.code() != 404) {
Toasty.info(context, context.getString(R.string.genericApiStatusError));
Toasty.error(context, context.getString(R.string.genericApiStatusError));
}
@ -129,10 +164,11 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
public void onFailure(@NonNull Call<WatchInfo> call, @NonNull Throwable t) {
tinyDb.putBoolean("repoWatch", false);
Toasty.info(context, context.getString(R.string.genericApiStatusError));
Toasty.error(context, context.getString(R.string.genericApiStatusError));
}
});
}
context.startActivity(intent);
@ -148,13 +184,26 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
TextView repoOpenInBrowser = view.findViewById(R.id.repoOpenInBrowser);
TextView repoStargazers = view.findViewById(R.id.repoStargazers);
TextView repoWatchers = view.findViewById(R.id.repoWatchers);
TextView repoForksList = view.findViewById(R.id.repoForksList);
TextView repoCopyUrl = view.findViewById(R.id.repoCopyUrl);
TextView bottomSheetHeader = view.findViewById(R.id.bottomSheetHeader);
bottomSheetHeader.setText(fullName.getText());
bottomSheetHeader.setText(String.format("%s / %s", fullName.getText().toString().split("/")[0], fullName.getText().toString().split("/")[1]));
BottomSheetDialog dialog = new BottomSheetDialog(context);
dialog.setContentView(view);
dialog.show();
repoCopyUrl.setOnClickListener(openInBrowser -> {
ClipboardManager clipboard = (ClipboardManager) Objects.requireNonNull(context).getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText("repoUrl", htmlUrl.getText().toString());
assert clipboard != null;
clipboard.setPrimaryClip(clip);
Toasty.info(context, context.getString(R.string.copyIssueUrlToastMsg));
dialog.dismiss();
});
repoOpenInBrowser.setOnClickListener(openInBrowser -> {
Intent intentOpenInBrowser = new Intent(context, OpenRepoInBrowserActivity.class);
@ -182,6 +231,15 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
});
repoForksList.setOnClickListener(forks -> {
Intent intentW = new Intent(context, RepoForksActivity.class);
intentW.putExtra("repoFullNameForForks", fullName.getText());
context.startActivity(intentW);
dialog.dismiss();
});
});
}
@ -208,6 +266,8 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
UserRepositories currentItem = reposList.get(position);
holder.repoDescription.setVisibility(View.GONE);
holder.repoBranch.setText(currentItem.getDefault_branch());
holder.htmlUrl.setText(currentItem.getHtml_url());
ColorGenerator generator = ColorGenerator.MATERIAL;
int color = generator.getColor(currentItem.getName());
@ -232,13 +292,13 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
holder.repoDescription.setVisibility(View.VISIBLE);
holder.repoDescription.setText(currentItem.getDescription());
}
holder.fullName.setText(currentItem.getFullname());
holder.fullName.setText(currentItem.getFullName());
if(currentItem.getPrivateFlag()) {
holder.repoPrivatePublic.setImageResource(R.drawable.ic_lock_bold);
holder.repoPrivatePublic.setImageResource(R.drawable.ic_lock);
holder.repoType.setText(R.string.strPrivate);
}
else {
holder.repoPrivatePublic.setImageResource(R.drawable.ic_public);
holder.repoPrivatePublic.setVisibility(View.GONE);
holder.repoType.setText(R.string.strPublic);
}
holder.repoStars.setText(currentItem.getStars_count());
@ -249,6 +309,13 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
}
holder.isRepoAdmin.setChecked(currentItem.getPermissions().isAdmin());
if(currentItem.isArchived()) {
holder.archiveRepo.setVisibility(View.VISIBLE);
}
else {
holder.archiveRepo.setVisibility(View.GONE);
}
}
@Override
@ -277,7 +344,7 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
String filterPattern = constraint.toString().toLowerCase().trim();
for(UserRepositories item : reposListFull) {
if(item.getFullname().toLowerCase().contains(filterPattern) || item.getDescription().toLowerCase().contains(filterPattern)) {
if(item.getFullName().toLowerCase().contains(filterPattern) || item.getDescription().toLowerCase().contains(filterPattern)) {
filteredList.add(item);
}
}

View File

@ -1,6 +1,8 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.ClipData;
import android.content.ClipboardManager;
import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
@ -11,7 +13,10 @@ import android.widget.CheckBox;
import android.widget.Filter;
import android.widget.Filterable;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import com.amulyakhare.textdrawable.TextDrawable;
import com.amulyakhare.textdrawable.util.ColorGenerator;
import com.google.android.material.bottomsheet.BottomSheetDialog;
@ -20,17 +25,19 @@ import org.mian.gitnex.activities.OpenRepoInBrowserActivity;
import org.mian.gitnex.activities.RepoDetailActivity;
import org.mian.gitnex.activities.RepoStargazersActivity;
import org.mian.gitnex.activities.RepoWatchersActivity;
import org.mian.gitnex.activities.RepoForksActivity;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.RepositoriesApi;
import org.mian.gitnex.database.models.Repository;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.UserRepositories;
import org.mian.gitnex.models.WatchInfo;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import java.util.Objects;
import retrofit2.Call;
import retrofit2.Callback;
@ -56,6 +63,9 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
private TextView repoForks;
private TextView repoOpenIssuesCount;
private TextView repoType;
private LinearLayout archiveRepo;
private TextView repoBranch;
private TextView htmlUrl;
private OrgReposViewHolder(View itemView) {
super(itemView);
@ -70,6 +80,9 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
repoOpenIssuesCount = itemView.findViewById(R.id.repoOpenIssuesCount);
ImageView reposDropdownMenu = itemView.findViewById(R.id.reposDropdownMenu);
repoType = itemView.findViewById(R.id.repoType);
archiveRepo = itemView.findViewById(R.id.archiveRepoFrame);
repoBranch = itemView.findViewById(R.id.repoBranch);
htmlUrl = itemView.findViewById(R.id.htmlUrl);
itemView.setOnClickListener(v -> {
@ -83,16 +96,36 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
tinyDb.putString("repoType", repoType.getText().toString());
//tinyDb.putBoolean("resumeIssues", true);
tinyDb.putBoolean("isRepoAdmin", isRepoAdmin.isChecked());
tinyDb.putString("repoBranch", repoBranch.getText().toString());
//store if user is watching this repo
{
final String instanceUrl = tinyDb.getString("instanceUrl");
String[] parts = fullName.getText().toString().split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
final String token = "token " + tinyDb.getString(tinyDb.getString("loginUid") + "-token");
WatchInfo watch = new WatchInfo();
int currentActiveAccountId = tinyDb.getInt("currentActiveAccountId");
RepositoriesApi repositoryData = new RepositoriesApi(context);
//RepositoriesRepository.deleteRepositoriesByAccount(currentActiveAccountId);
Integer count = repositoryData.checkRepository(currentActiveAccountId, repoOwner, repoName);
if(count == 0) {
long id = repositoryData.insertRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", id);
}
else {
Repository data = repositoryData.getRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", data.getRepositoryId());
}
//store if user is watching this repo
{
final String instanceUrl = tinyDb.getString("instanceUrl");
final String token = "token " + tinyDb.getString(tinyDb.getString("loginUid") + "-token");
Call<WatchInfo> call;
@ -114,7 +147,7 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
if(response.code() != 404) {
Toasty.info(context, context.getString(R.string.genericApiStatusError));
Toasty.error(context, context.getString(R.string.genericApiStatusError));
}
@ -126,10 +159,11 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
public void onFailure(@NonNull Call<WatchInfo> call, @NonNull Throwable t) {
tinyDb.putBoolean("repoWatch", false);
Toasty.info(context, context.getString(R.string.genericApiStatusError));
Toasty.error(context, context.getString(R.string.genericApiStatusError));
}
});
}
context.startActivity(intent);
@ -145,13 +179,26 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
TextView repoOpenInBrowser = view.findViewById(R.id.repoOpenInBrowser);
TextView repoStargazers = view.findViewById(R.id.repoStargazers);
TextView repoWatchers = view.findViewById(R.id.repoWatchers);
TextView repoForksList = view.findViewById(R.id.repoForksList);
TextView repoCopyUrl = view.findViewById(R.id.repoCopyUrl);
TextView bottomSheetHeader = view.findViewById(R.id.bottomSheetHeader);
bottomSheetHeader.setText(fullName.getText());
bottomSheetHeader.setText(String.format("%s / %s", fullName.getText().toString().split("/")[0], fullName.getText().toString().split("/")[1]));
BottomSheetDialog dialog = new BottomSheetDialog(context);
dialog.setContentView(view);
dialog.show();
repoCopyUrl.setOnClickListener(openInBrowser -> {
ClipboardManager clipboard = (ClipboardManager) Objects.requireNonNull(context).getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText("repoUrl", htmlUrl.getText().toString());
assert clipboard != null;
clipboard.setPrimaryClip(clip);
Toasty.info(context, context.getString(R.string.copyIssueUrlToastMsg));
dialog.dismiss();
});
repoOpenInBrowser.setOnClickListener(openInBrowser -> {
Intent intentOpenInBrowser = new Intent(context, OpenRepoInBrowserActivity.class);
@ -161,7 +208,7 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
});
repoStargazers.setOnClickListener(openInBrowser -> {
repoStargazers.setOnClickListener(stargazers -> {
Intent intent = new Intent(context, RepoStargazersActivity.class);
intent.putExtra("repoFullNameForStars", fullName.getText());
@ -170,7 +217,7 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
});
repoWatchers.setOnClickListener(openInBrowser -> {
repoWatchers.setOnClickListener(watchers -> {
Intent intentW = new Intent(context, RepoWatchersActivity.class);
intentW.putExtra("repoFullNameForWatchers", fullName.getText());
@ -179,6 +226,15 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
});
repoForksList.setOnClickListener(forks -> {
Intent intentW = new Intent(context, RepoForksActivity.class);
intentW.putExtra("repoFullNameForForks", fullName.getText());
context.startActivity(intentW);
dialog.dismiss();
});
});
}
@ -203,6 +259,8 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
UserRepositories currentItem = reposList.get(position);
holder.repoDescription.setVisibility(View.GONE);
holder.repoBranch.setText(currentItem.getDefault_branch());
holder.htmlUrl.setText(currentItem.getHtml_url());
ColorGenerator generator = ColorGenerator.MATERIAL;
int color = generator.getColor(currentItem.getName());
@ -234,13 +292,13 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
holder.repoDescription.setVisibility(View.VISIBLE);
holder.repoDescription.setText(currentItem.getDescription());
}
holder.fullName.setText(currentItem.getFullname());
holder.fullName.setText(currentItem.getFullName());
if(currentItem.getPrivateFlag()) {
holder.repoPrivatePublic.setImageResource(R.drawable.ic_lock_bold);
holder.repoPrivatePublic.setImageResource(R.drawable.ic_lock);
holder.repoType.setText(R.string.strPrivate);
}
else {
holder.repoPrivatePublic.setImageResource(R.drawable.ic_public);
holder.repoPrivatePublic.setVisibility(View.GONE);
holder.repoType.setText(R.string.strPublic);
}
holder.repoStars.setText(currentItem.getStars_count());
@ -252,6 +310,13 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
}
holder.isRepoAdmin.setChecked(currentItem.getPermissions().isAdmin());
if(currentItem.isArchived()) {
holder.archiveRepo.setVisibility(View.VISIBLE);
}
else {
holder.archiveRepo.setVisibility(View.GONE);
}
}
@Override
@ -275,7 +340,7 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
String filterPattern = constraint.toString().toLowerCase().trim();
for (UserRepositories item : reposListFull) {
if (item.getFullname().toLowerCase().contains(filterPattern) || item.getDescription().toLowerCase().contains(filterPattern)) {
if (item.getFullName().toLowerCase().contains(filterPattern) || item.getDescription().toLowerCase().contains(filterPattern)) {
filteredList.add(item);
}
}

View File

@ -1,6 +1,8 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.ClipData;
import android.content.ClipboardManager;
import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
@ -11,7 +13,10 @@ import android.widget.CheckBox;
import android.widget.Filter;
import android.widget.Filterable;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import com.amulyakhare.textdrawable.TextDrawable;
import com.amulyakhare.textdrawable.util.ColorGenerator;
import com.google.android.material.bottomsheet.BottomSheetDialog;
@ -20,17 +25,19 @@ import org.mian.gitnex.activities.OpenRepoInBrowserActivity;
import org.mian.gitnex.activities.RepoDetailActivity;
import org.mian.gitnex.activities.RepoStargazersActivity;
import org.mian.gitnex.activities.RepoWatchersActivity;
import org.mian.gitnex.activities.RepoForksActivity;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.database.api.RepositoriesApi;
import org.mian.gitnex.database.models.Repository;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.UserRepositories;
import org.mian.gitnex.models.WatchInfo;
import org.mian.gitnex.util.TinyDB;
import java.util.ArrayList;
import java.util.List;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import java.util.Objects;
import retrofit2.Call;
import retrofit2.Callback;
@ -56,6 +63,9 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
private TextView repoForks;
private TextView repoOpenIssuesCount;
private TextView repoType;
private LinearLayout archiveRepo;
private TextView repoBranch;
private TextView htmlUrl;
private StarredReposViewHolder(View itemView) {
super(itemView);
@ -70,6 +80,9 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
repoOpenIssuesCount = itemView.findViewById(R.id.repoOpenIssuesCount);
ImageView reposDropdownMenu = itemView.findViewById(R.id.reposDropdownMenu);
repoType = itemView.findViewById(R.id.repoType);
archiveRepo = itemView.findViewById(R.id.archiveRepoFrame);
repoBranch = itemView.findViewById(R.id.repoBranch);
htmlUrl = itemView.findViewById(R.id.htmlUrl);
itemView.setOnClickListener(v -> {
@ -83,13 +96,35 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
tinyDb.putString("repoType", repoType.getText().toString());
//tinyDb.putBoolean("resumeIssues", true);
tinyDb.putBoolean("isRepoAdmin", isRepoAdmin.isChecked());
tinyDb.putString("repoBranch", repoBranch.getText().toString());
//store if user is watching this repo
{
final String instanceUrl = tinyDb.getString("instanceUrl");
String[] parts = fullName.getText().toString().split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
int currentActiveAccountId = tinyDb.getInt("currentActiveAccountId");
RepositoriesApi repositoryData = new RepositoriesApi(context);
//RepositoriesRepository.deleteRepositoriesByAccount(currentActiveAccountId);
Integer count = repositoryData.checkRepository(currentActiveAccountId, repoOwner, repoName);
if(count == 0) {
long id = repositoryData.insertRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", id);
}
else {
Repository data = repositoryData.getRepository(currentActiveAccountId, repoOwner, repoName);
tinyDb.putLong("repositoryId", data.getRepositoryId());
}
//store if user is watching this repo
{
final String instanceUrl = tinyDb.getString("instanceUrl");
final String token = "token " + tinyDb.getString(tinyDb.getString("loginUid") + "-token");
WatchInfo watch = new WatchInfo();
@ -130,6 +165,7 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
}
});
}
context.startActivity(intent);
@ -146,13 +182,26 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
TextView repoOpenInBrowser = view.findViewById(R.id.repoOpenInBrowser);
TextView repoStargazers = view.findViewById(R.id.repoStargazers);
TextView repoWatchers = view.findViewById(R.id.repoWatchers);
TextView repoForksList = view.findViewById(R.id.repoForksList);
TextView repoCopyUrl = view.findViewById(R.id.repoCopyUrl);
TextView bottomSheetHeader = view.findViewById(R.id.bottomSheetHeader);
bottomSheetHeader.setText(fullName.getText());
bottomSheetHeader.setText(String.format("%s / %s", fullName.getText().toString().split("/")[0], fullName.getText().toString().split("/")[1]));
BottomSheetDialog dialog = new BottomSheetDialog(context);
dialog.setContentView(view);
dialog.show();
repoCopyUrl.setOnClickListener(openInBrowser -> {
ClipboardManager clipboard = (ClipboardManager) Objects.requireNonNull(context).getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText("repoUrl", htmlUrl.getText().toString());
assert clipboard != null;
clipboard.setPrimaryClip(clip);
Toasty.info(context, context.getString(R.string.copyIssueUrlToastMsg));
dialog.dismiss();
});
repoOpenInBrowser.setOnClickListener(openInBrowser -> {
Intent intentOpenInBrowser = new Intent(context, OpenRepoInBrowserActivity.class);
@ -180,6 +229,15 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
});
repoForksList.setOnClickListener(forks -> {
Intent intentW = new Intent(context, RepoForksActivity.class);
intentW.putExtra("repoFullNameForForks", fullName.getText());
context.startActivity(intentW);
dialog.dismiss();
});
});
}
@ -204,6 +262,8 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
UserRepositories currentItem = reposList.get(position);
holder.repoDescription.setVisibility(View.GONE);
holder.repoBranch.setText(currentItem.getDefault_branch());
holder.htmlUrl.setText(currentItem.getHtml_url());
ColorGenerator generator = ColorGenerator.MATERIAL;
int color = generator.getColor(currentItem.getName());
@ -235,13 +295,13 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
holder.repoDescription.setVisibility(View.VISIBLE);
holder.repoDescription.setText(currentItem.getDescription());
}
holder.fullName.setText(currentItem.getFullname());
holder.fullName.setText(currentItem.getFullName());
if(currentItem.getPrivateFlag()) {
holder.repoPrivatePublic.setImageResource(R.drawable.ic_lock_bold);
holder.repoPrivatePublic.setImageResource(R.drawable.ic_lock);
holder.repoType.setText(R.string.strPrivate);
}
else {
holder.repoPrivatePublic.setImageResource(R.drawable.ic_public);
holder.repoPrivatePublic.setVisibility(View.GONE);
holder.repoType.setText(R.string.strPublic);
}
holder.repoStars.setText(currentItem.getStars_count());
@ -252,6 +312,13 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
}
holder.isRepoAdmin.setChecked(currentItem.getPermissions().isAdmin());
if(currentItem.isArchived()) {
holder.archiveRepo.setVisibility(View.VISIBLE);
}
else {
holder.archiveRepo.setVisibility(View.GONE);
}
}
@Override
@ -275,7 +342,7 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
String filterPattern = constraint.toString().toLowerCase().trim();
for (UserRepositories item : reposListFull) {
if (item.getFullname().toLowerCase().contains(filterPattern) || item.getDescription().toLowerCase().contains(filterPattern)) {
if (item.getFullName().toLowerCase().contains(filterPattern) || item.getDescription().toLowerCase().contains(filterPattern)) {
filteredList.add(item);
}
}

View File

@ -11,10 +11,9 @@ import android.widget.ImageView;
import android.widget.TextView;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.helpers.FontsOverride;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
/**
@ -111,12 +110,5 @@ public class TeamMembersByOrgAdapter extends BaseAdapter {
viewHolder.memberName.setTypeface(myTypeface);
}
if(tinyDb.getInt("themeId") == 1) { //light
viewHolder.memberName.setTextColor(mCtx.getResources().getColor(R.color.lightThemeTextColor));
}
else { // dark
viewHolder.memberName.setTextColor(mCtx.getResources().getColor(R.color.white));
}
}
}

View File

@ -0,0 +1,155 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AlertDialog;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.database.api.UserAccountsApi;
import org.mian.gitnex.database.models.UserAccount;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import java.util.List;
import io.mikael.urlbuilder.UrlBuilder;
/**
* Author M M Arif
*/
public class UserAccountsAdapter extends RecyclerView.Adapter<UserAccountsAdapter.UserAccountsViewHolder> {
private List<UserAccount> userAccountsList;
private Context mCtx;
private TinyDB tinyDB;
class UserAccountsViewHolder extends RecyclerView.ViewHolder {
private TextView accountUrl;
private TextView userId;
private ImageView activeAccount;
private ImageView deleteAccount;
private ImageView repoAvatar;
private TextView accountId;
private TextView accountName;
private UserAccountsViewHolder(View itemView) {
super(itemView);
accountUrl = itemView.findViewById(R.id.accountUrl);
userId = itemView.findViewById(R.id.userId);
activeAccount = itemView.findViewById(R.id.activeAccount);
deleteAccount = itemView.findViewById(R.id.deleteAccount);
repoAvatar = itemView.findViewById(R.id.repoAvatar);
accountId = itemView.findViewById(R.id.accountId);
accountName = itemView.findViewById(R.id.accountName);
deleteAccount.setOnClickListener(itemDelete -> {
new AlertDialog.Builder(mCtx)
.setIcon(mCtx.getDrawable(R.drawable.ic_delete))
.setTitle(mCtx.getResources().getString(R.string.removeAccountPopupTitle))
.setMessage(mCtx.getResources().getString(R.string.removeAccountPopupMessage))
.setPositiveButton(mCtx.getResources().getString(R.string.removeButton), (dialog, which) -> {
updateLayoutByPosition(getAdapterPosition());
UserAccountsApi userAccountsApi = new UserAccountsApi(mCtx);
userAccountsApi.deleteAccount(Integer.parseInt(accountId.getText().toString()));
}).setNeutralButton(mCtx.getResources().getString(R.string.cancelButton), null)
.show();
});
itemView.setOnClickListener(itemEdit -> {
String accountNameSwitch = accountName.getText().toString();
UserAccountsApi userAccountsApi = new UserAccountsApi(mCtx);
UserAccount userAccount = userAccountsApi.getAccountData(accountNameSwitch);
if(tinyDB.getInt("currentActiveAccountId") != userAccount.getAccountId()) {
String url = UrlBuilder.fromString(userAccount.getInstanceUrl())
.withPath("/")
.toString();
tinyDB.putString("loginUid", userAccount.getUserName());
tinyDB.putString("userLogin", userAccount.getUserName());
tinyDB.putString(userAccount.getUserName() + "-token", userAccount.getToken());
tinyDB.putString("instanceUrl", userAccount.getInstanceUrl());
tinyDB.putInt("currentActiveAccountId", userAccount.getAccountId());
Toasty.success(mCtx, mCtx.getResources().getString(R.string.switchAccountSuccess, userAccount.getUserName(), url));
((Activity) mCtx).recreate();
}
});
}
}
public UserAccountsAdapter(Context mCtx, List<UserAccount> userAccountsListMain) {
this.mCtx = mCtx;
this.userAccountsList = userAccountsListMain;
}
private void updateLayoutByPosition(int position) {
userAccountsList.remove(position);
notifyItemRemoved(position);
notifyItemRangeChanged(position, userAccountsList.size());
Toasty.success(mCtx, mCtx.getResources().getString(R.string.accountDeletedMessage));
}
@NonNull
@Override
public UserAccountsAdapter.UserAccountsViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.list_user_accounts, parent, false);
return new UserAccountsViewHolder(v);
}
@SuppressLint("DefaultLocale")
@Override
public void onBindViewHolder(@NonNull UserAccountsAdapter.UserAccountsViewHolder holder, int position) {
UserAccount currentItem = userAccountsList.get(position);
tinyDB = new TinyDB(mCtx);
String url = UrlBuilder.fromString(currentItem.getInstanceUrl())
.withPath("/")
.toString();
holder.accountId.setText(String.valueOf(currentItem.getAccountId()));
holder.accountName.setText(currentItem.getAccountName());
holder.userId.setText(String.format("@%s", currentItem.getUserName()));
holder.accountUrl.setText(url);
PicassoService.getInstance(mCtx).get().load(url + "img/favicon.png").placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(120, 120).centerCrop().into(holder.repoAvatar);
if(tinyDB.getInt("currentActiveAccountId") == currentItem.getAccountId()) {
holder.activeAccount.setVisibility(View.VISIBLE);
}
else {
holder.deleteAccount.setVisibility(View.VISIBLE);
}
}
@Override
public int getItemCount() {
return userAccountsList.size();
}
}

View File

@ -0,0 +1,76 @@
package org.mian.gitnex.adapters;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ArrayAdapter;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.database.models.UserAccount;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import java.util.List;
import io.mikael.urlbuilder.UrlBuilder;
/**
* Author M M Arif
*/
public class UserAccountsListDialogAdapter extends ArrayAdapter<UserAccount> {
private final Context mCtx;
private final TinyDB tinyDB;
private final List<UserAccount> userAccounts;
public UserAccountsListDialogAdapter(@NonNull Context mCtx, int resource, @NonNull List<UserAccount> userAccounts) {
super(mCtx, resource, userAccounts);
tinyDB = new TinyDB(mCtx);
this.userAccounts = userAccounts;
this.mCtx = mCtx;
}
@NonNull
@Override
public View getView(int position, @Nullable View convertView, @NonNull ViewGroup parent) {
if(convertView == null) {
convertView = LayoutInflater.from(mCtx).inflate(R.layout.custom_user_accounts_list, parent, false);
}
ImageView profileImage = convertView.findViewById(R.id.profileImage);
TextView userName = convertView.findViewById(R.id.userName);
TextView accountUrl = convertView.findViewById(R.id.accountUrl);
ImageView activeAccount = convertView.findViewById(R.id.activeAccount);
UserAccount currentItem = userAccounts.get(position);
String url = UrlBuilder.fromString(currentItem.getInstanceUrl())
.withPath("/")
.toString();
userName.setText(currentItem.getUserName());
accountUrl.setText(url);
if(tinyDB.getInt("currentActiveAccountId") == currentItem.getAccountId()) {
activeAccount.setVisibility(View.VISIBLE);
}
else {
activeAccount.setVisibility(View.GONE);
}
PicassoService
.getInstance(mCtx).get().load(url + "img/favicon.png").placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(120, 120).centerCrop().into(profileImage);
return convertView;
}
}

View File

@ -0,0 +1,147 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.app.Dialog;
import android.content.Context;
import android.graphics.Color;
import android.graphics.drawable.ColorDrawable;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.ListView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import androidx.drawerlayout.widget.DrawerLayout;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.clients.PicassoService;
import org.mian.gitnex.database.api.UserAccountsApi;
import org.mian.gitnex.database.models.UserAccount;
import org.mian.gitnex.fragments.UserAccountsFragment;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import java.util.List;
import io.mikael.urlbuilder.UrlBuilder;
/**
* Author M M Arif
*/
public class UserAccountsNavAdapter extends RecyclerView.Adapter<UserAccountsNavAdapter.UserAccountsViewHolder> {
private static DrawerLayout drawer;
private List<UserAccount> userAccountsList;
private Context mCtx;
private TextView toolbarTitle;
public UserAccountsNavAdapter(Context mCtx, List<UserAccount> userAccountsListMain, DrawerLayout drawerLayout, TextView toolbarTitle) {
this.mCtx = mCtx;
this.userAccountsList = userAccountsListMain;
drawer = drawerLayout;
this.toolbarTitle = toolbarTitle;
}
class UserAccountsViewHolder extends RecyclerView.ViewHolder {
private ImageView userAccountAvatar;
private UserAccountsViewHolder(View itemView) {
super(itemView);
userAccountAvatar = itemView.findViewById(R.id.userAccountAvatar);
itemView.setOnClickListener(item -> {
customDialogUserAccountsList(userAccountsList);
drawer.closeDrawers();
});
}
}
@NonNull
@Override
public UserAccountsNavAdapter.UserAccountsViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
View v = LayoutInflater.from(parent.getContext()).inflate(R.layout.nav_user_accounts, parent, false);
return new UserAccountsViewHolder(v);
}
@SuppressLint("DefaultLocale")
@Override
public void onBindViewHolder(@NonNull UserAccountsNavAdapter.UserAccountsViewHolder holder, int position) {
UserAccount currentItem = userAccountsList.get(position);
String url = UrlBuilder.fromString(currentItem.getInstanceUrl())
.withPath("/")
.toString();
PicassoService
.getInstance(mCtx).get().load(url + "img/favicon.png").placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(120, 120).centerCrop().into(holder.userAccountAvatar);
}
@Override
public int getItemCount() {
return userAccountsList.size();
}
private void customDialogUserAccountsList(List<UserAccount> allAccountsList) {
TinyDB tinyDB = new TinyDB(mCtx);
Dialog dialog = new Dialog(mCtx, R.style.ThemeOverlay_MaterialComponents_Dialog_Alert);
dialog.setContentView(R.layout.custom_user_accounts_dialog);
ListView listView = dialog.findViewById(R.id.accountsList);
TextView manageAccounts = dialog.findViewById(R.id.manageAccounts);
if (dialog.getWindow() != null) {
dialog.getWindow().setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
}
manageAccounts.setOnClickListener(item -> {
toolbarTitle.setText(mCtx.getResources().getString(R.string.pageTitleUserAccounts));
AppCompatActivity activity = (AppCompatActivity) mCtx;
activity.getSupportFragmentManager().beginTransaction().replace(R.id.fragment_container, new UserAccountsFragment()).commit();
dialog.dismiss();
});
UserAccountsListDialogAdapter arrayAdapter = new UserAccountsListDialogAdapter(mCtx, R.layout.custom_user_accounts_list, allAccountsList);
listView.setAdapter(arrayAdapter);
listView.setOnItemClickListener((adapterView, view, which, l) -> {
String accountNameSwitch = allAccountsList.get(which).getAccountName();
UserAccountsApi userAccountsApi = new UserAccountsApi(mCtx);
UserAccount userAccount = userAccountsApi.getAccountData(accountNameSwitch);
if(tinyDB.getInt("currentActiveAccountId") != userAccount.getAccountId()) {
String url = UrlBuilder.fromString(userAccount.getInstanceUrl())
.withPath("/")
.toString();
tinyDB.putString("loginUid", userAccount.getUserName());
tinyDB.putString("userLogin", userAccount.getUserName());
tinyDB.putString(userAccount.getUserName() + "-token", userAccount.getToken());
tinyDB.putString("instanceUrl", userAccount.getInstanceUrl());
tinyDB.putInt("currentActiveAccountId", userAccount.getAccountId());
Toasty.success(mCtx, mCtx.getResources().getString(R.string.switchAccountSuccess, userAccount.getUserName(), url));
((Activity) mCtx).recreate();
dialog.dismiss();
}
});
dialog.show();
}
}

View File

@ -9,6 +9,9 @@ import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.ListView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AlertDialog;
import androidx.recyclerview.widget.RecyclerView;
import org.mian.gitnex.R;
import org.mian.gitnex.actions.CollaboratorActions;
import org.mian.gitnex.clients.PicassoService;
@ -16,13 +19,10 @@ import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.models.Collaborators;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AlertDialog;
import androidx.recyclerview.widget.RecyclerView;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;

View File

@ -14,9 +14,9 @@ import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.helpers.AlertDialogs;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.Toasty;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
@ -104,12 +104,11 @@ public class UserSearchForTeamMemberAdapter extends RecyclerView.Adapter<UserSea
if (!currentItem.getFullname().equals("")) {
holder.userFullName.setText(currentItem.getFullname());
holder.userName.setText(mCtx.getResources().getString(R.string.usernameWithAt, currentItem.getLogin()));
}
else {
holder.userFullName.setText(mCtx.getResources().getString(R.string.usernameWithAt, currentItem.getLogin()));
holder.userName.setText(mCtx.getResources().getString(R.string.usernameWithAt, currentItem.getLogin()));
}
holder.userName.setText(mCtx.getResources().getString(R.string.usernameWithAt, currentItem.getLogin()));
if (!currentItem.getAvatar().equals("")) {
PicassoService.getInstance(mCtx).get().load(currentItem.getAvatar()).placeholder(R.drawable.loader_animated).transform(new RoundedTransformation(8, 0)).resize(120, 120).centerCrop().into(holder.userAvatar);
@ -123,7 +122,6 @@ public class UserSearchForTeamMemberAdapter extends RecyclerView.Adapter<UserSea
String repoFullName = tinyDb.getString("repoFullName");
String[] parts = repoFullName.split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
Call<UserInfo> call = RetrofitClient

View File

@ -2,10 +2,10 @@ package org.mian.gitnex.clients;
import android.content.Context;
import android.util.Log;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.FilesData;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.ssl.MemorizingTrustManager;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.io.File;
import java.security.SecureRandom;
import javax.net.ssl.HttpsURLConnection;
@ -27,7 +27,7 @@ public class AppApiService {
public static <S> S createService(Class<S> serviceClass, String instanceURL, Context ctx) {
TinyDB tinyDb = new TinyDB(ctx);
final boolean connToInternet = AppUtil.haveNetworkConnection(ctx);
final boolean connToInternet = AppUtil.hasNetworkConnection(ctx);
File httpCacheDirectory = new File(ctx.getCacheDir(), "responses");
int cacheSize = FilesData.returnOnlyNumber(tinyDb.getString("cacheSizeStr")) * 1024 * 1024;
Cache cache = new Cache(httpCacheDirectory, cacheSize);

View File

@ -14,16 +14,18 @@ import javax.net.ssl.X509TrustManager;
import okhttp3.OkHttpClient;
/**
* Author anonTree1417
* Author opyale
*/
public class PicassoService {
private static PicassoService picassoService;
private static File cachePath;
private Picasso picasso;
private PicassoService(Context context) {
cachePath = new File(context.getCacheDir() + "/picasso_cache/");
Picasso.Builder builder = new Picasso.Builder(context);
try {
@ -45,10 +47,6 @@ public class PicassoService {
});
File cachePath = new File(context.getCacheDir() + "/picasso_cache/");
//noinspection ResultOfMethodCallIgnored
cachePath.mkdirs();
picasso = builder.memoryCache(new PicassoCache(cachePath, context)).build();
}
@ -61,7 +59,9 @@ public class PicassoService {
public Picasso get() {
cachePath.mkdirs();
return picasso;
}
public static synchronized PicassoService getInstance(Context context) {

View File

@ -2,12 +2,12 @@ package org.mian.gitnex.clients;
import android.content.Context;
import android.util.Log;
import org.mian.gitnex.helpers.AppUtil;
import org.mian.gitnex.helpers.FilesData;
import org.mian.gitnex.helpers.TinyDB;
import org.mian.gitnex.helpers.ssl.MemorizingTrustManager;
import org.mian.gitnex.interfaces.ApiInterface;
import org.mian.gitnex.interfaces.WebInterface;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.io.File;
import java.security.SecureRandom;
import javax.net.ssl.HttpsURLConnection;
@ -32,7 +32,7 @@ public class RetrofitClient {
private RetrofitClient(String instanceUrl, Context ctx) {
TinyDB tinyDb = new TinyDB(ctx);
final boolean connToInternet = AppUtil.haveNetworkConnection(ctx);
final boolean connToInternet = AppUtil.hasNetworkConnection(ctx);
int cacheSize = FilesData.returnOnlyNumber(tinyDb.getString("cacheSizeStr")) * 1024 * 1024;
File httpCacheDirectory = new File(ctx.getCacheDir(), "responses");
Cache cache = new Cache(httpCacheDirectory, cacheSize);

View File

@ -0,0 +1,126 @@
package org.mian.gitnex.database.api;
import android.content.Context;
import android.util.Log;
import androidx.lifecycle.LiveData;
import org.mian.gitnex.database.dao.DraftsDao;
import org.mian.gitnex.database.db.GitnexDatabase;
import org.mian.gitnex.database.models.Draft;
import org.mian.gitnex.database.models.DraftWithRepository;
import org.mian.gitnex.helpers.StaticGlobalVariables;
import java.util.List;
/**
* Author M M Arif
*/
public class DraftsApi {
private static DraftsDao draftsDao;
private static long draftId;
private static Integer checkDraftFlag;
public DraftsApi(Context context) {
GitnexDatabase db;
db = GitnexDatabase.getDatabaseInstance(context);
draftsDao = db.draftsDao();
}
public long insertDraft(int repositoryId, int draftAccountId, int issueId, String draftText, String draftType, String commentId) {
Draft draft = new Draft();
draft.setDraftRepositoryId(repositoryId);
draft.setDraftAccountId(draftAccountId);
draft.setIssueId(issueId);
draft.setDraftText(draftText);
draft.setDraftType(draftType);
draft.setCommentId(draftType);
return insertDraftAsyncTask(draft);
}
private static long insertDraftAsyncTask(final Draft draft) {
try {
Thread thread = new Thread(() -> draftId = draftsDao.insertDraft(draft));
thread.start();
thread.join();
}
catch(InterruptedException e) {
Log.e(StaticGlobalVariables.draftsRepository, e.toString());
}
return draftId;
}
public long getDraftIdAsync(int issueId, int draftRepositoryId) {
try {
Thread thread = new Thread(() -> draftId = draftsDao.getDraftId(issueId, draftRepositoryId));
thread.start();
thread.join();
}
catch(InterruptedException e) {
Log.e(StaticGlobalVariables.draftsRepository, e.toString());
}
return draftId;
}
public Integer checkDraft(int issueId, int draftRepositoryId, String commentId) {
try {
Thread thread = new Thread(() -> checkDraftFlag = draftsDao.checkDraftDao(issueId, draftRepositoryId, commentId));
thread.start();
thread.join();
}
catch(InterruptedException e) {
Log.e(StaticGlobalVariables.draftsRepository, e.toString());
}
return checkDraftFlag;
}
public LiveData<List<DraftWithRepository>> getDrafts(int accountId) {
return draftsDao.fetchAllDrafts(accountId);
}
public LiveData<Draft> getDraftByIssueId(int issueId) {
return draftsDao.fetchDraftByIssueId(issueId);
}
public void deleteSingleDraft(final int draftId) {
final LiveData<Draft> draft = draftsDao.fetchDraftById(draftId);
if(draft != null) {
new Thread(() -> draftsDao.deleteByDraftId(draftId)).start();
}
}
public static void deleteAllDrafts(final int accountId) {
new Thread(() -> draftsDao.deleteAllDrafts(accountId)).start();
}
public static void updateDraft(final String draftText, final int draftId, final String commentId) {
new Thread(() -> draftsDao.updateDraft(draftText, draftId, commentId)).start();
}
public static void updateDraftByIssueIdAsyncTask(final String draftText, final int issueId, final int draftRepositoryId, final String commentId) {
new Thread(() -> draftsDao.updateDraftByIssueId(draftText, issueId, draftRepositoryId, commentId)).start();
}
}

View File

@ -0,0 +1,145 @@
package org.mian.gitnex.database.api;
import android.content.Context;
import android.util.Log;
import androidx.lifecycle.LiveData;
import org.mian.gitnex.database.dao.RepositoriesDao;
import org.mian.gitnex.database.db.GitnexDatabase;
import org.mian.gitnex.database.models.Repository;
import org.mian.gitnex.helpers.StaticGlobalVariables;
import java.util.List;
/**
* Author M M Arif
*/
public class RepositoriesApi {
private static RepositoriesDao repositoriesDao;
private static long repositoryId;
private static Repository repository;
private static Integer checkRepository;
public RepositoriesApi(Context context) {
GitnexDatabase db;
db = GitnexDatabase.getDatabaseInstance(context);
repositoriesDao = db.repositoriesDao();
}
public long insertRepository(int repoAccountId, String repositoryOwner, String repositoryName) {
Repository repository = new Repository();
repository.setRepoAccountId(repoAccountId);
repository.setRepositoryOwner(repositoryOwner);
repository.setRepositoryName(repositoryName);
return insertRepositoryAsyncTask(repository);
}
public long insertRepositoryAsyncTask(Repository repository) {
try {
Thread thread = new Thread(() -> repositoryId = repositoriesDao.newRepository(repository));
thread.start();
thread.join();
}
catch(InterruptedException e) {
Log.e(StaticGlobalVariables.repositoriesRepository, e.toString());
}
return repositoryId;
}
public Repository getRepository(int repoAccountId, String repositoryOwner, String repositoryName) {
try {
Thread thread = new Thread(() -> repository = repositoriesDao.getSingleRepositoryDao(repoAccountId, repositoryOwner, repositoryName));
thread.start();
thread.join();
}
catch(InterruptedException e) {
Log.e(StaticGlobalVariables.repositoriesRepository, e.toString());
}
return repository;
}
public LiveData<List<Repository>> getAllRepositories() {
return repositoriesDao.fetchAllRepositories();
}
public LiveData<List<Repository>> getAllRepositoriesByAccount(int repoAccountId) {
return repositoriesDao.getAllRepositoriesByAccountDao(repoAccountId);
}
public Integer checkRepository(int repoAccountId, String repositoryOwner, String repositoryName) {
try {
Thread thread = new Thread(() -> checkRepository = repositoriesDao.checkRepositoryDao(repoAccountId, repositoryOwner, repositoryName));
thread.start();
thread.join();
}
catch(InterruptedException e) {
Log.e(StaticGlobalVariables.repositoriesRepository, e.toString());
}
return checkRepository;
}
public Repository fetchRepositoryById(int repositoryId) {
try {
Thread thread = new Thread(() -> repository = repositoriesDao.fetchRepositoryByIdDao(repositoryId));
thread.start();
thread.join();
}
catch(InterruptedException e) {
Log.e(StaticGlobalVariables.repositoriesRepository, e.toString());
}
return repository;
}
public Repository fetchRepositoryByAccountIdByRepositoryId(int repositoryId, int repoAccountId) {
try {
Thread thread = new Thread(() -> repository = repositoriesDao.fetchRepositoryByAccountIdByRepositoryIdDao(repositoryId, repoAccountId));
thread.start();
thread.join();
}
catch(InterruptedException e) {
Log.e(StaticGlobalVariables.repositoriesRepository, e.toString());
}
return repository;
}
public static void updateRepositoryOwnerAndName(String repositoryOwner, String repositoryName, int repositoryId) {
new Thread(() -> repositoriesDao.updateRepositoryOwnerAndName(repositoryOwner, repositoryName, repositoryId)).start();
}
public static void deleteRepositoriesByAccount(final int repoAccountId) {
new Thread(() -> repositoriesDao.deleteRepositoriesByAccount(repoAccountId)).start();
}
public static void deleteRepository(final int repositoryId) {
new Thread(() -> repositoriesDao.deleteRepository(repositoryId)).start();
}
}

Some files were not shown because too many files have changed in this diff Show More