Compare commits

..

38 Commits
1.5.0 ... 2.0.0

Author SHA1 Message Date
da268b017e Merge branch 'prepare-2-0-release' of mmarif/GitNex into master 2019-09-18 10:27:06 +00:00
4451adb01c prepare for release 2019-09-18 15:02:33 +05:00
0cd4e36a66 Merge branch '16-create-files' of mmarif/GitNex into master 2019-09-18 09:51:27 +00:00
742b1894e6 finished work on creating new file 2019-09-18 14:49:29 +05:00
8d1b47de8e wip on creating new file. still has to do branches section for old and new. 2019-09-18 13:25:49 +05:00
c38d249571 new file layout and bottomsheet link 2019-09-17 11:17:05 +05:00
c3da1900a0 add donator to sponsor page, file icon 2019-09-17 09:24:32 +05:00
b4c0745b40 reduce large links in branches and releases to small text with links.
Signed-off-by: M M Arif <mmarif@swatian.com>
2019-09-16 20:28:34 +05:00
e8e0cf904b Merge branch '37-fix-crash-within-tabs' of mmarif/GitNex into master 2019-09-14 09:43:54 +00:00
99718bc0c8 fix branches hash url 2019-09-14 14:40:47 +05:00
d4a5d5ee8c fix url linking for repo website 2019-09-14 13:22:01 +05:00
efffc05a89 fix crash on tabs, other ui fixes 2019-09-14 13:20:00 +05:00
a78018fd08 Merge branch '36-open-repo-in-browser' of mmarif/GitNex into master 2019-09-14 07:41:00 +00:00
33d1373f6e added open in browser 2019-09-14 12:38:41 +05:00
b15394e97d Add browser icon and xml element in menu 2019-09-14 12:26:20 +05:00
2bdeee5429 Merge branch '24-list-repo-watchers' of mmarif/GitNex into master 2019-09-14 06:55:22 +00:00
39c1ec36a7 Added repo watchers/subscribrs list 2019-09-14 11:29:20 +05:00
6866154714 Merge branch '25-list-repo-stargazers' of mmarif/GitNex into master 2019-09-13 16:03:29 +00:00
df260f05d2 added stargazers and other fixes and enhancements 2019-09-13 20:56:30 +05:00
d24e7ffc3b Add dotted menu 2019-09-13 12:21:52 +05:00
481451c791 Merge branch '23-fixes' of mmarif/GitNex into master 2019-09-12 08:32:00 +00:00
914d5cfa26 libs update, fixes search tap crashing. remove depricated classes 2019-09-12 13:30:07 +05:00
6710aa0810 clean up unwanted namespaces from layouts 2019-09-12 10:29:41 +05:00
87376a2104 Fix collaborator not found text 2019-09-12 10:21:53 +05:00
1ec7ac4f9f Merge branch 'open-repo-web' of 6543/GitNex into master 2019-09-11 06:26:58 +00:00
25f8277f0a translate missing with deepl 2019-09-10 19:56:54 +02:00
498bf7a72c spelling corection 2019-09-10 19:51:43 +02:00
20f687e30e add sugestions of mmarif
* delete OpenWebRepoActivity (function is handled in RepoDetailActivity )
 * add&handle case "openWebRepo" in RepoDetailActivity
 * add new Value "instanceUrlWithProtocol" to tinyDb
2019-09-10 19:48:44 +02:00
83e3564c13 try to implement OpenWebRepoActivity 2019-09-06 01:01:46 +02:00
7977aaa2be shorter text 2019-09-05 22:19:26 +02:00
6bc13ad4fe ues language icon also to indicate webbrowser open action 2019-09-05 22:06:23 +02:00
1f6f50977e Merge branch 'german-translation' of 6543/GitNex into master 2019-09-05 10:09:51 +00:00
1ce1278095 tiny lang. changes 2019-09-03 16:55:51 +02:00
ce63cde4ee add menue entry and strings 2019-09-03 16:46:38 +02:00
f23c4074f3 Merge branch 'master' of PsychotherapistSam/GitNex into master 2019-07-18 10:43:17 +00:00
ace9111225 Update 'app/src/main/res/values-de/strings.xml'
Updated some of the german translations :)
2019-07-18 03:44:16 +00:00
4aeeb95308 Merge branch 'fix-contribute-file' of mmarif/GitNex into master 2019-06-24 10:04:55 +00:00
056413e0b0 fix wordings 2019-06-24 02:33:30 +05:00
103 changed files with 2352 additions and 352 deletions

View File

@ -3,14 +3,14 @@
Please take a few minutes to read this document to make the process of contribution more easy and healthy for all involved.
## Pull Requests
Patches, enhancements, features are always welcome. The MR should focus on the scope of work and avoid many unnecessary commits. Please provide as much detail and context as possible to explain the work submitted.
Patches, enhancements, features are always welcome. The PR should focus on the scope of work and avoid many unnecessary commits. Please provide as much detail and context as possible to explain the work submitted.
Please ask if you are not sure about the scope of work to be submitted to avoid waste of time spent on the work.
**How to submit MR/PR**
**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.
**IMPORTANT:** By submitting MR, you agree to allow GitNex to license your work under the same license as that used by GitNex.
**IMPORTANT:** By submitting PR, you agree to allow GitNex to license your work under the same license as that used by GitNex.
## Issues and Reports
*1st of please be polite and gentle while commenting or creating new issue to maintain a healthy environment.*

View File

@ -6,8 +6,8 @@ android {
applicationId "org.mian.gitnex"
minSdkVersion 21
targetSdkVersion 28
versionCode 45
versionName "1.5.0"
versionCode 55
versionName "2.0.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
}
buildTypes {
@ -23,12 +23,12 @@ android {
}
dependencies {
def lifecycle_version = "2.2.0-alpha01"
def lifecycle_version = "2.2.0-alpha04"
final def markwon_version = "3.0.0"
implementation fileTree(include: ['*.jar'], dir: 'libs')
implementation 'androidx.appcompat:appcompat:1.1.0-beta01'
implementation 'com.google.android.material:material:1.1.0-alpha07'
implementation 'androidx.appcompat:appcompat:1.1.0'
implementation 'com.google.android.material:material:1.1.0-alpha10'
implementation 'androidx.constraintlayout:constraintlayout:1.1.3'
implementation 'androidx.legacy:legacy-support-v4:1.0.0'
testImplementation 'junit:junit:4.12'

View File

@ -2,9 +2,6 @@
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="org.mian.gitnex">
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<application
android:allowBackup="true"
android:icon="@mipmap/app_logo"
@ -13,7 +10,16 @@
android:roundIcon="@mipmap/app_logo_round"
android:supportsRtl="true"
android:theme="@style/AppTheme">
<activity android:name=".activities.AdminGetUsersActivity"></activity>
<activity
android:name=".activities.NewFileActivity"
android:theme="@style/AppTheme.NoActionBar"></activity>
<activity
android:name=".activities.RepoWatchersActivity"
android:theme="@style/AppTheme.NoActionBar" />
<activity
android:name=".activities.RepoStargazersActivity"
android:theme="@style/AppTheme.NoActionBar" />
<activity android:name=".activities.AdminGetUsersActivity" />
<activity
android:name=".activities.AddRemoveAssigneesActivity"
android:theme="@style/Theme.AppCompat.Light.Dialog" />
@ -56,6 +62,10 @@
android:launchMode="singleTask" />
<activity android:name=".activities.NewRepoActivity" />
<activity android:name=".activities.NewOrganizationActivity" />
<activity android:name=".activities.OpenRepoInBrowserActivity" />
</application>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.INTERNET" />
</manifest>

View File

@ -194,16 +194,20 @@ public class LoginActivity extends AppCompatActivity implements View.OnClickList
instanceHost = instanceUrl;
}
String instanceUrlWithProtocol;
if(protocol.toLowerCase().equals("https")) {
instanceUrl = "https://" + instanceHost + "/api/v1/";
instanceUrlWithProtocol = "https://" + instanceHost;
}
else {
instanceUrl = "http://" + instanceHost + "/api/v1/";
instanceUrlWithProtocol = "https://" + instanceHost;
}
tinyDb.putString("instanceUrlRaw", instanceHost);
tinyDb.putString("loginUid", loginUid);
tinyDb.putString("instanceUrl", instanceUrl);
tinyDb.putString("instanceUrlWithProtocol", instanceUrlWithProtocol);
if(connToInternet) {

View File

@ -330,6 +330,9 @@ public class MainActivity extends AppCompatActivity implements NavigationView.On
if (response.code() == 200) {
assert userDetails != null;
if(userDetails.getIs_admin() != null) {
tinyDb.putBoolean("userIsAdmin", userDetails.getIs_admin());
}
tinyDb.putString("userLogin", userDetails.getLogin());
tinyDb.putInt("userId", userDetails.getId());
if(!userDetails.getFullname().equals("")) {

View File

@ -0,0 +1,335 @@
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;
import android.widget.AdapterView;
import android.widget.ArrayAdapter;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.Spinner;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
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.Toasty;
import org.mian.gitnex.models.Branches;
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;
import retrofit2.Callback;
/**
* Author M M Arif
*/
public class NewFileActivity extends AppCompatActivity {
public ImageView closeActivity;
private View.OnClickListener onClickListener;
private Button newFileCreate;
private EditText newFileName;
private EditText newFileContent;
private EditText newFileBranchName;
private EditText newFileCommitMessage;
private Spinner newFileBranchesSpinner;
final Context ctx = this;
List<Branches> branchesList = new ArrayList<>();
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_new_file);
boolean connToInternet = AppUtil.haveNetworkConnection(getApplicationContext());
TinyDB tinyDb = new TinyDB(getApplicationContext());
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");
closeActivity = findViewById(R.id.close);
newFileName = findViewById(R.id.newFileName);
newFileContent = findViewById(R.id.newFileContent);
newFileBranchName = findViewById(R.id.newFileBranchName);
newFileCommitMessage = findViewById(R.id.newFileCommitMessage);
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
newFileCreate = findViewById(R.id.newFileCreate);
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()
{
public void onItemSelected(AdapterView<?> arg0,
View arg1, int arg2, long arg3)
{
Branches bModelValue = (Branches) newFileBranchesSpinner.getSelectedItem();
Log.i("bModelSelected", bModelValue.toString());
if(bModelValue.toString().equals("No branch")) {
newFileBranchName.setEnabled(true);
}
else {
newFileBranchName.setEnabled(false);
newFileBranchName.setText("");
}
}
public void onNothingSelected(AdapterView<?> arg0) {}
});
disableProcessButton();
if(!connToInternet) {
newFileCreate.setEnabled(false);
GradientDrawable shape = new GradientDrawable();
shape.setCornerRadius( 8 );
shape.setColor(getResources().getColor(R.color.hintColor));
newFileCreate.setBackground(shape);
} else {
newFileCreate.setOnClickListener(createFileListener);
}
}
private View.OnClickListener createFileListener = new View.OnClickListener() {
public void onClick(View v) {
processNewFile();
}
};
private void processNewFile() {
boolean connToInternet = AppUtil.haveNetworkConnection(getApplicationContext());
AppUtil appUtil = new AppUtil();
TinyDB tinyDb = new TinyDB(getApplicationContext());
final String instanceUrl = tinyDb.getString("instanceUrl");
final String loginUid = tinyDb.getString("loginUid");
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
String repoFullName = tinyDb.getString("repoFullName");
String[] parts = repoFullName.split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
String newFileName_ = newFileName.getText().toString();
String newFileContent_ = newFileContent.getText().toString();
String newFileBranchName_ = newFileBranchName.getText().toString();
String newFileCommitMessage_ = newFileCommitMessage.getText().toString();
Branches currentBranch = (Branches) newFileBranchesSpinner.getSelectedItem();
if(!connToInternet) {
Toasty.info(getApplicationContext(), getResources().getString(R.string.checkNetConnection));
return;
}
if(newFileName_.equals("") || newFileContent_.equals("") || newFileCommitMessage_.equals("")) {
Toasty.info(getApplicationContext(), getString(R.string.newFileRequiredFields));
return;
}
if(currentBranch.toString().equals("No branch")) {
if(newFileBranchName_.equals("")) {
Toasty.info(getApplicationContext(), getString(R.string.newFileRequiredFieldNewBranchName));
return;
}
else {
if(!appUtil.checkStringsWithDash(newFileBranchName_)) {
Toasty.info(getApplicationContext(), getString(R.string.newFileInvalidBranchName));
return;
}
}
}
if(appUtil.charactersLength(newFileCommitMessage_) > 255) {
Toasty.info(getApplicationContext(), getString(R.string.newFileCommitMessageError));
}
else {
disableProcessButton();
createNewFile(instanceUrl, Authorization.returnAuthentication(getApplicationContext(), loginUid, instanceToken), repoOwner, repoName, newFileName_, appUtil.encodeBase64(newFileContent_), newFileBranchName_, newFileCommitMessage_, currentBranch.toString());
}
}
private void createNewFile(final String instanceUrl, final String token, String repoOwner, String repoName, String fileName, String fileContent, String fileBranchName, String fileCommitMessage, String currentBranch) {
NewFile createNewFileJsonStr;
if(currentBranch.equals("No branch")) {
createNewFileJsonStr = new NewFile("", fileContent, fileCommitMessage, fileBranchName);
}
else {
createNewFileJsonStr = new NewFile(currentBranch, fileContent, fileCommitMessage, "");
}
Call<JsonElement> call = RetrofitClient
.getInstance(instanceUrl)
.getApiInterface()
.createNewFile(token, repoOwner, repoName, fileName, createNewFileJsonStr);
call.enqueue(new Callback<JsonElement>() {
@Override
public void onResponse(@NonNull Call<JsonElement> call, @NonNull retrofit2.Response<JsonElement> response) {
if(response.code() == 201) {
enableProcessButton();
Toasty.info(getApplicationContext(), getString(R.string.newFileSuccessMessage));
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(getApplicationContext(), getString(R.string.apiNotFound));
}
else {
enableProcessButton();
Toasty.info(getApplicationContext(), getString(R.string.orgCreatedError));
}
}
}
@Override
public void onFailure(@NonNull Call<JsonElement> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
enableProcessButton();
}
});
}
private void getBranches(String instanceUrl, String instanceToken, String repoOwner, String repoName, String loginUid) {
Call<List<Branches>> call = RetrofitClient
.getInstance(instanceUrl)
.getApiInterface()
.getBranches(Authorization.returnAuthentication(getApplicationContext(), 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();
branchesList.add(new Branches("No branch"));
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<>(getApplicationContext(),
R.layout.spinner_item, branchesList);
adapter.setDropDownViewResource(R.layout.spinner_dropdown_item);
newFileBranchesSpinner.setAdapter(adapter);
enableProcessButton();
}
}
}
@Override
public void onFailure(@NonNull Call<List<Branches>> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
}
});
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
}
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

@ -0,0 +1,35 @@
package org.mian.gitnex.activities;
import android.content.Intent;
import android.net.Uri;
import android.os.Bundle;
import androidx.appcompat.app.AppCompatActivity;
import org.mian.gitnex.util.TinyDB;
/**
* Author M M Arif
*/
public class OpenRepoInBrowserActivity extends AppCompatActivity {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
TinyDB tinyDb = new TinyDB(getApplicationContext());
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);
startActivity(i);
finish();
}
}

View File

@ -3,9 +3,8 @@ package org.mian.gitnex.activities;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.widget.GridView;
import android.widget.ImageView;
@ -63,7 +62,7 @@ public class OrgTeamMembersActivity extends AppCompatActivity {
}
getIntent().getStringExtra("teamId");
Log.i("teamId", getIntent().getStringExtra("teamId"));
//Log.i("teamId", getIntent().getStringExtra("teamId"));
fetchDataAsync(instanceUrl, Authorization.returnAuthentication(getApplicationContext(), loginUid, instanceToken), Integer.valueOf(teamId));
@ -71,7 +70,7 @@ public class OrgTeamMembersActivity extends AppCompatActivity {
private void fetchDataAsync(String instanceUrl, String instanceToken, int teamId) {
TeamMembersByOrgViewModel teamMembersModel = ViewModelProviders.of(this).get(TeamMembersByOrgViewModel.class);
TeamMembersByOrgViewModel teamMembersModel = new ViewModelProvider(this).get(TeamMembersByOrgViewModel.class);
teamMembersModel.getMembersByOrgList(instanceUrl, instanceToken, teamId).observe(this, new Observer<List<UserInfo>>() {
@Override

View File

@ -35,6 +35,7 @@ import org.mian.gitnex.models.UserRepositories;
import org.mian.gitnex.util.AppUtil;
import org.mian.gitnex.util.TinyDB;
import java.util.Objects;
import android.net.Uri;
/**
* Author M M Arif
@ -107,7 +108,6 @@ public class RepoDetailActivity extends AppCompatActivity implements RepoBottomS
}
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
@ -153,6 +153,20 @@ public class RepoDetailActivity extends AppCompatActivity implements RepoBottomS
case "createRelease":
startActivity(new Intent(RepoDetailActivity.this, CreateReleaseActivity.class));
break;
case "openWebRepo":
TinyDB tinyDb = new TinyDB(getApplicationContext());
String repoFullName = tinyDb.getString("repoFullName");
String instanceUrlWithProtocol = "https://" + tinyDb.getString("instanceUrlRaw");
if(!tinyDb.getString("instanceUrlWithProtocol").isEmpty()) {
instanceUrlWithProtocol = tinyDb.getString("instanceUrlWithProtocol");
}
Uri url = Uri.parse(instanceUrlWithProtocol + "/" + repoFullName);
Intent i = new Intent(Intent.ACTION_VIEW, url);
startActivity(i);
break;
case "newFile":
startActivity(new Intent(RepoDetailActivity.this, NewFileActivity.class));
break;
}
}
@ -160,7 +174,7 @@ public class RepoDetailActivity extends AppCompatActivity implements RepoBottomS
public class SectionsPagerAdapter extends FragmentStatePagerAdapter {
SectionsPagerAdapter(FragmentManager fm) {
super(fm);
super(fm, BEHAVIOR_RESUME_ONLY_CURRENT_FRAGMENT);
}
@NonNull

View File

@ -0,0 +1,95 @@
package org.mian.gitnex.activities;
import android.os.Bundle;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
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 org.mian.gitnex.R;
import org.mian.gitnex.adapters.RepoStargazersAdapter;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.viewmodels.RepoStargazersViewModel;
import java.util.List;
/**
* Author M M Arif
*/
public class RepoStargazersActivity extends AppCompatActivity {
private TextView noDataStargazers;
private View.OnClickListener onClickListener;
private RepoStargazersAdapter adapter;
private GridView mGridView;
private ProgressBar mProgressBar;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_repo_stargazers);
TinyDB tinyDb = new TinyDB(getApplicationContext());
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);
TextView toolbarTitle = findViewById(R.id.toolbar_title);
noDataStargazers = findViewById(R.id.noDataStargazers);
mGridView = findViewById(R.id.gridView);
mProgressBar = findViewById(R.id.progress_bar);
String repoFullNameForStars = getIntent().getStringExtra("repoFullNameForStars");
String[] parts = repoFullNameForStars.split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
toolbarTitle.setText(R.string.repoStargazersInMenu);
fetchDataAsync(instanceUrl, Authorization.returnAuthentication(getApplicationContext(), loginUid, instanceToken), repoOwner, repoName);
}
private void fetchDataAsync(String instanceUrl, String instanceToken, String repoOwner, String repoName) {
RepoStargazersViewModel repoStargazersModel = new ViewModelProvider(this).get(RepoStargazersViewModel.class);
repoStargazersModel.getRepoStargazers(instanceUrl, instanceToken, repoOwner, repoName).observe(this, new Observer<List<UserInfo>>() {
@Override
public void onChanged(@Nullable List<UserInfo> stargazersListMain) {
adapter = new RepoStargazersAdapter(getApplicationContext(), stargazersListMain);
if(adapter.getCount() > 0) {
mGridView.setAdapter(adapter);
noDataStargazers.setVisibility(View.GONE);
}
else {
adapter.notifyDataSetChanged();
mGridView.setAdapter(adapter);
noDataStargazers.setVisibility(View.VISIBLE);
}
mProgressBar.setVisibility(View.GONE);
}
});
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
}
}

View File

@ -0,0 +1,95 @@
package org.mian.gitnex.activities;
import android.os.Bundle;
import androidx.annotation.Nullable;
import androidx.appcompat.app.AppCompatActivity;
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 org.mian.gitnex.R;
import org.mian.gitnex.adapters.RepoWatchersAdapter;
import org.mian.gitnex.helpers.Authorization;
import org.mian.gitnex.models.UserInfo;
import org.mian.gitnex.util.TinyDB;
import org.mian.gitnex.viewmodels.RepoWatchersViewModel;
import java.util.List;
/**
* Author M M Arif
*/
public class RepoWatchersActivity extends AppCompatActivity {
private TextView noDataWatchers;
private View.OnClickListener onClickListener;
private RepoWatchersAdapter adapter;
private GridView mGridView;
private ProgressBar mProgressBar;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_repo_watchers);
TinyDB tinyDb = new TinyDB(getApplicationContext());
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);
TextView toolbarTitle = findViewById(R.id.toolbar_title);
noDataWatchers = findViewById(R.id.noDataWatchers);
mGridView = findViewById(R.id.gridView);
mProgressBar = findViewById(R.id.progress_bar);
String repoFullNameForWatchers = getIntent().getStringExtra("repoFullNameForWatchers");
String[] parts = repoFullNameForWatchers.split("/");
final String repoOwner = parts[0];
final String repoName = parts[1];
initCloseListener();
closeActivity.setOnClickListener(onClickListener);
toolbarTitle.setText(R.string.repoWatchersInMenu);
fetchDataAsync(instanceUrl, Authorization.returnAuthentication(getApplicationContext(), loginUid, instanceToken), repoOwner, repoName);
}
private void fetchDataAsync(String instanceUrl, String instanceToken, String repoOwner, String repoName) {
RepoWatchersViewModel repoWatchersModel = new ViewModelProvider(this).get(RepoWatchersViewModel.class);
repoWatchersModel.getRepoWatchers(instanceUrl, instanceToken, repoOwner, repoName).observe(this, new Observer<List<UserInfo>>() {
@Override
public void onChanged(@Nullable List<UserInfo> watchersListMain) {
adapter = new RepoWatchersAdapter(getApplicationContext(), watchersListMain);
if(adapter.getCount() > 0) {
mGridView.setAdapter(adapter);
noDataWatchers.setVisibility(View.GONE);
}
else {
adapter.notifyDataSetChanged();
mGridView.setAdapter(adapter);
noDataWatchers.setVisibility(View.VISIBLE);
}
mProgressBar.setVisibility(View.GONE);
}
});
}
private void initCloseListener() {
onClickListener = new View.OnClickListener() {
@Override
public void onClick(View view) {
finish();
}
};
}
}

View File

@ -2,8 +2,10 @@ package org.mian.gitnex.activities;
import androidx.appcompat.app.AppCompatActivity;
import android.os.Bundle;
import android.text.method.LinkMovementMethod;
import android.view.View;
import android.widget.ImageView;
import android.widget.TextView;
import org.mian.gitnex.R;
/**
@ -20,6 +22,9 @@ public class SponsorsActivity extends AppCompatActivity {
setContentView(R.layout.activity_sponsors);
ImageView closeActivity = findViewById(R.id.close);
TextView liberaPaySponsorsThomas = findViewById(R.id.liberaPaySponsorsThomas);
liberaPaySponsorsThomas.setMovementMethod(LinkMovementMethod.getInstance());
initCloseListener();
closeActivity.setOnClickListener(onClickListener);

View File

@ -1,12 +1,13 @@
package org.mian.gitnex.adapters;
import android.content.Context;
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 org.mian.gitnex.R;
import org.mian.gitnex.helpers.UrlHelper;
import org.mian.gitnex.models.Branches;
import org.mian.gitnex.util.TinyDB;
import java.util.List;
@ -66,7 +67,9 @@ public class BranchesAdapter extends RecyclerView.Adapter<BranchesAdapter.Branch
holder.branchCommitAuthor.setText(mCtx.getResources().getString(R.string.commitAuthor, currentItem.getCommit().getAuthor().getUsername()));
}
holder.branchCommitHash.setText(mCtx.getResources().getString(R.string.commitHash, UrlHelper.cleanUrl(instanceUrl), currentItem.getCommit().getUrl()));
holder.branchCommitHash.setText(
Html.fromHtml("<a href='" + currentItem.getCommit().getUrl() + "'>" + mCtx.getResources().getString(R.string.commitLinkBranchesTab) + "</a> "));
holder.branchCommitHash.setMovementMethod(LinkMovementMethod.getInstance());
}

View File

@ -4,6 +4,7 @@ import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
import android.view.LayoutInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Filter;
@ -13,12 +14,18 @@ import android.widget.TextView;
import com.amulyakhare.textdrawable.TextDrawable;
import com.amulyakhare.textdrawable.util.ColorGenerator;
import org.mian.gitnex.R;
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.models.UserRepositories;
import org.mian.gitnex.util.TinyDB;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.List;
import androidx.annotation.NonNull;
import androidx.appcompat.view.ContextThemeWrapper;
import androidx.appcompat.widget.PopupMenu;
import androidx.recyclerview.widget.RecyclerView;
/**
@ -52,6 +59,7 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
repoStarsMy = itemView.findViewById(R.id.repoStarsMy);
repoWatchersMy = itemView.findViewById(R.id.repoWatchersMy);
repoOpenIssuesCountMy = itemView.findViewById(R.id.repoOpenIssuesCountMy);
ImageView reposDropdownMenu = itemView.findViewById(R.id.reposDropdownMenu);
itemView.setOnClickListener(new View.OnClickListener() {
@Override
@ -70,6 +78,69 @@ public class MyReposListAdapter extends RecyclerView.Adapter<MyReposListAdapter.
}
});
reposDropdownMenu.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
final Context context = v.getContext();
Context context_ = new ContextThemeWrapper(context, R.style.popupMenuStyle);
PopupMenu popupMenu = new PopupMenu(context_, v);
popupMenu.inflate(R.menu.repo_dotted_list_menu);
Object menuHelper;
Class[] argTypes;
try {
Field fMenuHelper = PopupMenu.class.getDeclaredField("mPopup");
fMenuHelper.setAccessible(true);
menuHelper = fMenuHelper.get(popupMenu);
argTypes = new Class[] { boolean.class };
menuHelper.getClass().getDeclaredMethod("setForceShowIcon",
argTypes).invoke(menuHelper, true);
} catch (Exception e) {
popupMenu.show();
return;
}
popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem item) {
switch (item.getItemId()) {
case R.id.repoStargazers:
Intent intent = new Intent(context, RepoStargazersActivity.class);
intent.putExtra("repoFullNameForStars", fullNameMy.getText());
context.startActivity(intent);
break;
case R.id.repoWatchers:
Intent intentW = new Intent(context, RepoWatchersActivity.class);
intentW.putExtra("repoFullNameForWatchers", fullNameMy.getText());
context.startActivity(intentW);
break;
case R.id.repoOpenInBrowser:
Intent intentOpenInBrowser = new Intent(context, OpenRepoInBrowserActivity.class);
intentOpenInBrowser.putExtra("repoFullNameBrowser", fullNameMy.getText());
context.startActivity(intentOpenInBrowser);
break;
}
return false;
}
});
popupMenu.show();
}
});
}
}

View File

@ -76,7 +76,6 @@ public class OrganizationsListAdapter extends RecyclerView.Adapter<Organizations
@Override
public void onBindViewHolder(@NonNull OrganizationsViewHolder holder, int position) {
UserOrganizations currentItem = orgList.get(position);
holder.mTextView2.setVisibility(View.GONE);

View File

@ -2,6 +2,8 @@ package org.mian.gitnex.adapters;
import android.content.Context;
import android.graphics.Color;
import android.text.Html;
import android.text.method.LinkMovementMethod;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
@ -139,8 +141,14 @@ public class ReleasesAdapter extends RecyclerView.Adapter<ReleasesAdapter.Releas
else {
holder.releaseDescription.setVisibility(View.GONE);
}
holder.releaseZipDownload.setText(currentItem.getZipball_url());
holder.releaseTarDownload.setText(currentItem.getTarball_url());
holder.releaseZipDownload.setText(
Html.fromHtml("<a href='" + currentItem.getZipball_url() + "'>" + mCtx.getResources().getString(R.string.zipArchiveDownloadReleasesTab) + "</a> "));
holder.releaseZipDownload.setMovementMethod(LinkMovementMethod.getInstance());
holder.releaseTarDownload.setText(
Html.fromHtml("<a href='" + currentItem.getTarball_url() + "'>" + mCtx.getResources().getString(R.string.tarArchiveDownloadReleasesTab) + "</a> "));
holder.releaseTarDownload.setMovementMethod(LinkMovementMethod.getInstance());
}

View File

@ -0,0 +1,91 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.TextView;
import com.squareup.picasso.Picasso;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.models.UserInfo;
import java.util.List;
/**
* Author M M Arif
*/
public class RepoStargazersAdapter extends BaseAdapter {
private List<UserInfo> stargazersList;
private Context mCtx;
private class ViewHolder {
private ImageView memberAvatar;
private TextView memberName;
ViewHolder(View v) {
memberAvatar = v.findViewById(R.id.memberAvatar);
memberName = v.findViewById(R.id.memberName);
}
}
public RepoStargazersAdapter(Context mCtx, List<UserInfo> membersListMain) {
this.mCtx = mCtx;
this.stargazersList = membersListMain;
}
@Override
public int getCount() {
return stargazersList.size();
}
@Override
public Object getItem(int position) {
return null;
}
@Override
public long getItemId(int position) {
return 0;
}
@SuppressLint("InflateParams")
@Override
public View getView(int position, View finalView, ViewGroup parent) {
RepoStargazersAdapter.ViewHolder viewHolder;
if (finalView == null) {
finalView = LayoutInflater.from(mCtx).inflate(R.layout.repo_stargazers_list, null);
viewHolder = new RepoStargazersAdapter.ViewHolder(finalView);
finalView.setTag(viewHolder);
}
else {
viewHolder = (RepoStargazersAdapter.ViewHolder) finalView.getTag();
}
initData(viewHolder, position);
return finalView;
}
private void initData(RepoStargazersAdapter.ViewHolder viewHolder, int position) {
UserInfo currentItem = stargazersList.get(position);
Picasso.get().load(currentItem.getAvatar()).transform(new RoundedTransformation(100, 0)).resize(200, 200).centerCrop().into(viewHolder.memberAvatar);
if(!currentItem.getFullname().equals("")) {
viewHolder.memberName.setText(currentItem.getFullname());
}
else {
viewHolder.memberName.setText(currentItem.getLogin());
}
}
}

View File

@ -0,0 +1,91 @@
package org.mian.gitnex.adapters;
import android.annotation.SuppressLint;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.BaseAdapter;
import android.widget.ImageView;
import android.widget.TextView;
import com.squareup.picasso.Picasso;
import org.mian.gitnex.R;
import org.mian.gitnex.helpers.RoundedTransformation;
import org.mian.gitnex.models.UserInfo;
import java.util.List;
/**
* Author M M Arif
*/
public class RepoWatchersAdapter extends BaseAdapter {
private List<UserInfo> watchersList;
private Context mCtx;
private class ViewHolder {
private ImageView memberAvatar;
private TextView memberName;
ViewHolder(View v) {
memberAvatar = v.findViewById(R.id.memberAvatar);
memberName = v.findViewById(R.id.memberName);
}
}
public RepoWatchersAdapter(Context mCtx, List<UserInfo> membersListMain) {
this.mCtx = mCtx;
this.watchersList = membersListMain;
}
@Override
public int getCount() {
return watchersList.size();
}
@Override
public Object getItem(int position) {
return null;
}
@Override
public long getItemId(int position) {
return 0;
}
@SuppressLint("InflateParams")
@Override
public View getView(int position, View finalView, ViewGroup parent) {
RepoWatchersAdapter.ViewHolder viewHolder;
if (finalView == null) {
finalView = LayoutInflater.from(mCtx).inflate(R.layout.repo_watchers_list, null);
viewHolder = new RepoWatchersAdapter.ViewHolder(finalView);
finalView.setTag(viewHolder);
}
else {
viewHolder = (RepoWatchersAdapter.ViewHolder) finalView.getTag();
}
initData(viewHolder, position);
return finalView;
}
private void initData(RepoWatchersAdapter.ViewHolder viewHolder, int position) {
UserInfo currentItem = watchersList.get(position);
Picasso.get().load(currentItem.getAvatar()).transform(new RoundedTransformation(100, 0)).resize(200, 200).centerCrop().into(viewHolder.memberAvatar);
if(!currentItem.getFullname().equals("")) {
viewHolder.memberName.setText(currentItem.getFullname());
}
else {
viewHolder.memberName.setText(currentItem.getLogin());
}
}
}

View File

@ -4,8 +4,11 @@ import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
import androidx.annotation.NonNull;
import androidx.appcompat.view.ContextThemeWrapper;
import androidx.appcompat.widget.PopupMenu;
import androidx.recyclerview.widget.RecyclerView;
import android.view.LayoutInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Filter;
@ -15,9 +18,13 @@ import android.widget.TextView;
import com.amulyakhare.textdrawable.TextDrawable;
import com.amulyakhare.textdrawable.util.ColorGenerator;
import org.mian.gitnex.R;
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.models.UserRepositories;
import org.mian.gitnex.util.TinyDB;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.List;
@ -43,6 +50,7 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
private TextView repoOpenIssuesCount;
private ReposViewHolder(View itemView) {
super(itemView);
mTextView1 = itemView.findViewById(R.id.repoName);
mTextView2 = itemView.findViewById(R.id.repoDescription);
@ -52,13 +60,14 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
repoStars = itemView.findViewById(R.id.repoStars);
repoWatchers = itemView.findViewById(R.id.repoWatchers);
repoOpenIssuesCount = itemView.findViewById(R.id.repoOpenIssuesCount);
ImageView reposDropdownMenu = itemView.findViewById(R.id.reposDropdownMenu);
itemView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
Context context = v.getContext();
TextView repoFullName = (TextView) v.findViewById(R.id.repoFullName);
TextView repoFullName = v.findViewById(R.id.repoFullName);
Intent intent = new Intent(context, RepoDetailActivity.class);
intent.putExtra("repoFullName", repoFullName.getText().toString());
@ -70,6 +79,70 @@ public class ReposListAdapter extends RecyclerView.Adapter<ReposListAdapter.Repo
}
});
reposDropdownMenu.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
final Context context = v.getContext();
Context context_ = new ContextThemeWrapper(context, R.style.popupMenuStyle);
PopupMenu popupMenu = new PopupMenu(context_, v);
popupMenu.inflate(R.menu.repo_dotted_list_menu);
Object menuHelper;
Class[] argTypes;
try {
Field fMenuHelper = PopupMenu.class.getDeclaredField("mPopup");
fMenuHelper.setAccessible(true);
menuHelper = fMenuHelper.get(popupMenu);
argTypes = new Class[] { boolean.class };
menuHelper.getClass().getDeclaredMethod("setForceShowIcon",
argTypes).invoke(menuHelper, true);
} catch (Exception e) {
popupMenu.show();
return;
}
popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem item) {
switch (item.getItemId()) {
case R.id.repoStargazers:
Intent intent = new Intent(context, RepoStargazersActivity.class);
intent.putExtra("repoFullNameForStars", fullName.getText());
context.startActivity(intent);
break;
case R.id.repoWatchers:
Intent intentW = new Intent(context, RepoWatchersActivity.class);
intentW.putExtra("repoFullNameForWatchers", fullName.getText());
context.startActivity(intentW);
break;
case R.id.repoOpenInBrowser:
Intent intentOpenInBrowser = new Intent(context, OpenRepoInBrowserActivity.class);
intentOpenInBrowser.putExtra("repoFullNameBrowser", fullName.getText());
context.startActivity(intentOpenInBrowser);
break;
}
return false;
}
});
popupMenu.show();
}
});
}
}

View File

@ -4,6 +4,7 @@ import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
import android.view.LayoutInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Filter;
@ -13,12 +14,18 @@ import android.widget.TextView;
import com.amulyakhare.textdrawable.TextDrawable;
import com.amulyakhare.textdrawable.util.ColorGenerator;
import org.mian.gitnex.R;
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.models.UserRepositories;
import org.mian.gitnex.util.TinyDB;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.List;
import androidx.annotation.NonNull;
import androidx.appcompat.view.ContextThemeWrapper;
import androidx.appcompat.widget.PopupMenu;
import androidx.recyclerview.widget.RecyclerView;
/**
@ -52,6 +59,7 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
repoStars = itemView.findViewById(R.id.repoStars);
repoWatchers = itemView.findViewById(R.id.repoWatchers);
repoOpenIssuesCount = itemView.findViewById(R.id.repoOpenIssuesCount);
ImageView reposDropdownMenu = itemView.findViewById(R.id.reposDropdownMenu);
itemView.setOnClickListener(new View.OnClickListener() {
@Override
@ -70,6 +78,69 @@ public class RepositoriesByOrgAdapter extends RecyclerView.Adapter<RepositoriesB
}
});
reposDropdownMenu.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
final Context context = v.getContext();
Context context_ = new ContextThemeWrapper(context, R.style.popupMenuStyle);
PopupMenu popupMenu = new PopupMenu(context_, v);
popupMenu.inflate(R.menu.repo_dotted_list_menu);
Object menuHelper;
Class[] argTypes;
try {
Field fMenuHelper = PopupMenu.class.getDeclaredField("mPopup");
fMenuHelper.setAccessible(true);
menuHelper = fMenuHelper.get(popupMenu);
argTypes = new Class[] { boolean.class };
menuHelper.getClass().getDeclaredMethod("setForceShowIcon",
argTypes).invoke(menuHelper, true);
} catch (Exception e) {
popupMenu.show();
return;
}
popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem item) {
switch (item.getItemId()) {
case R.id.repoStargazers:
Intent intent = new Intent(context, RepoStargazersActivity.class);
intent.putExtra("repoFullNameForStars", fullName.getText());
context.startActivity(intent);
break;
case R.id.repoWatchers:
Intent intentW = new Intent(context, RepoWatchersActivity.class);
intentW.putExtra("repoFullNameForWatchers", fullName.getText());
context.startActivity(intentW);
break;
case R.id.repoOpenInBrowser:
Intent intentOpenInBrowser = new Intent(context, OpenRepoInBrowserActivity.class);
intentOpenInBrowser.putExtra("repoFullNameBrowser", fullName.getText());
context.startActivity(intentOpenInBrowser);
break;
}
return false;
}
});
popupMenu.show();
}
});
}
}

View File

@ -4,6 +4,7 @@ import android.content.Context;
import android.content.Intent;
import android.graphics.Typeface;
import android.view.LayoutInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
import android.widget.Filter;
@ -13,12 +14,18 @@ import android.widget.TextView;
import com.amulyakhare.textdrawable.TextDrawable;
import com.amulyakhare.textdrawable.util.ColorGenerator;
import org.mian.gitnex.R;
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.models.UserRepositories;
import org.mian.gitnex.util.TinyDB;
import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.List;
import androidx.annotation.NonNull;
import androidx.appcompat.view.ContextThemeWrapper;
import androidx.appcompat.widget.PopupMenu;
import androidx.recyclerview.widget.RecyclerView;
/**
@ -52,6 +59,7 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
repoStars = itemView.findViewById(R.id.repoStars);
repoWatchers = itemView.findViewById(R.id.repoWatchers);
repoOpenIssuesCount = itemView.findViewById(R.id.repoOpenIssuesCount);
ImageView reposDropdownMenu = itemView.findViewById(R.id.reposDropdownMenu);
itemView.setOnClickListener(new View.OnClickListener() {
@Override
@ -70,6 +78,69 @@ public class StarredReposListAdapter extends RecyclerView.Adapter<StarredReposLi
}
});
reposDropdownMenu.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
final Context context = v.getContext();
Context context_ = new ContextThemeWrapper(context, R.style.popupMenuStyle);
PopupMenu popupMenu = new PopupMenu(context_, v);
popupMenu.inflate(R.menu.repo_dotted_list_menu);
Object menuHelper;
Class[] argTypes;
try {
Field fMenuHelper = PopupMenu.class.getDeclaredField("mPopup");
fMenuHelper.setAccessible(true);
menuHelper = fMenuHelper.get(popupMenu);
argTypes = new Class[] { boolean.class };
menuHelper.getClass().getDeclaredMethod("setForceShowIcon",
argTypes).invoke(menuHelper, true);
} catch (Exception e) {
popupMenu.show();
return;
}
popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
@Override
public boolean onMenuItemClick(MenuItem item) {
switch (item.getItemId()) {
case R.id.repoStargazers:
Intent intent = new Intent(context, RepoStargazersActivity.class);
intent.putExtra("repoFullNameForStars", fullName.getText());
context.startActivity(intent);
break;
case R.id.repoWatchers:
Intent intentW = new Intent(context, RepoWatchersActivity.class);
intentW.putExtra("repoFullNameForWatchers", fullName.getText());
context.startActivity(intentW);
break;
case R.id.repoOpenInBrowser:
Intent intentOpenInBrowser = new Intent(context, OpenRepoInBrowserActivity.class);
intentOpenInBrowser.putExtra("repoFullNameBrowser", fullName.getText());
context.startActivity(intentOpenInBrowser);
break;
}
return false;
}
});
popupMenu.show();
}
});
}
}

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -125,7 +125,7 @@ public class BranchesFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken, String owner, String repo) {
BranchesViewModel branchesModel = ViewModelProviders.of(this).get(BranchesViewModel.class);
BranchesViewModel branchesModel = new ViewModelProvider(this).get(BranchesViewModel.class);
branchesModel.getBranchesList(instanceUrl, instanceToken, owner, repo).observe(this, new Observer<List<Branches>>() {
@Override

View File

@ -6,11 +6,12 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.GridView;
import android.widget.ProgressBar;
import android.widget.TextView;
import org.mian.gitnex.R;
import org.mian.gitnex.adapters.CollaboratorsAdapter;
@ -26,6 +27,7 @@ import java.util.List;
public class CollaboratorsFragment extends Fragment {
private ProgressBar mProgressBar;
private CollaboratorsAdapter adapter;
private GridView mGridView;
private TextView noDataCollaborators;
@ -69,6 +71,8 @@ public class CollaboratorsFragment extends Fragment {
final String instanceToken = "token " + tinyDb.getString(loginUid + "-token");
noDataCollaborators = v.findViewById(R.id.noDataCollaborators);
mProgressBar = v.findViewById(R.id.progress_bar);
mGridView = v.findViewById(R.id.gridView);
fetchDataAsync(instanceUrl, Authorization.returnAuthentication(getContext(), loginUid, instanceToken), repoOwner, repoName);
@ -94,7 +98,7 @@ public class CollaboratorsFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken, String owner, String repo) {
CollaboratorsViewModel collaboratorsModel = ViewModelProviders.of(this).get(CollaboratorsViewModel.class);
CollaboratorsViewModel collaboratorsModel = new ViewModelProvider(this).get(CollaboratorsViewModel.class);
collaboratorsModel.getCollaboratorsList(instanceUrl, instanceToken, owner, repo).observe(this, new Observer<List<Collaborators>>() {
@Override
@ -109,6 +113,7 @@ public class CollaboratorsFragment extends Fragment {
mGridView.setAdapter(adapter);
noDataCollaborators.setVisibility(View.VISIBLE);
}
mProgressBar.setVisibility(View.GONE);
}
});

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -142,7 +142,7 @@ public class LabelsFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken, String owner, String repo) {
LabelsViewModel labelsModel = ViewModelProviders.of(this).get(LabelsViewModel.class);
LabelsViewModel labelsModel = new ViewModelProvider(this).get(LabelsViewModel.class);
labelsModel.getLabelsList(instanceUrl, instanceToken, owner, repo).observe(this, new Observer<List<Labels>>() {
@Override

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
@ -81,7 +81,7 @@ public class MembersByOrgFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken, String owner) {
MembersByOrgViewModel membersModel = ViewModelProviders.of(this).get(MembersByOrgViewModel.class);
MembersByOrgViewModel membersModel= new ViewModelProvider(this).get(MembersByOrgViewModel.class);
membersModel.getMembersList(instanceUrl, instanceToken, owner).observe(this, new Observer<List<UserInfo>>() {
@Override
@ -125,7 +125,9 @@ public class MembersByOrgFragment extends Fragment {
@Override
public boolean onQueryTextChange(String newText) {
if(mGridView.getAdapter() != null) {
adapter.getFilter().filter(newText);
}
return false;
}
});

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -150,7 +150,7 @@ public class MilestonesFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken, String owner, String repo) {
MilestonesViewModel msModel = ViewModelProviders.of(this).get(MilestonesViewModel.class);
MilestonesViewModel msModel = new ViewModelProvider(this).get(MilestonesViewModel.class);
msModel.getMilestonesList(instanceUrl, instanceToken, owner, repo).observe(this, new Observer<List<Milestones>>() {
@Override
@ -195,7 +195,9 @@ public class MilestonesFragment extends Fragment {
@Override
public boolean onQueryTextChange(String newText) {
if(mRecyclerView.getAdapter() != null) {
adapter.getFilter().filter(newText);
}
return false;
}
});

View File

@ -7,7 +7,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -171,7 +171,7 @@ public class MyRepositoriesFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken, String username) {
MyRepositoriesViewModel myRepoModel = ViewModelProviders.of(this).get(MyRepositoriesViewModel.class);
MyRepositoriesViewModel myRepoModel = new ViewModelProvider(this).get(MyRepositoriesViewModel.class);
myRepoModel.getCurrentUserRepositories(instanceUrl, instanceToken, username).observe(this, new Observer<List<UserRepositories>>() {
@Override
@ -216,7 +216,9 @@ public class MyRepositoriesFragment extends Fragment {
@Override
public boolean onQueryTextChange(String newText) {
if(mRecyclerView.getAdapter() != null) {
adapter.getFilter().filter(newText);
}
return false;
}
});

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -141,7 +141,7 @@ public class OrganizationsFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken) {
OrganizationListViewModel orgModel = ViewModelProviders.of(this).get(OrganizationListViewModel.class);
OrganizationListViewModel orgModel = new ViewModelProvider(this).get(OrganizationListViewModel.class);
orgModel.getUserOrgs(instanceUrl, instanceToken).observe(this, new Observer<List<UserOrganizations>>() {
@Override
@ -186,7 +186,9 @@ public class OrganizationsFragment extends Fragment {
@Override
public boolean onQueryTextChange(String newText) {
if(mRecyclerView.getAdapter() != null) {
adapter.getFilter().filter(newText);
}
return false;
}
});

View File

@ -5,7 +5,7 @@ import android.os.Bundle;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -109,7 +109,7 @@ public class ProfileEmailsFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken) {
ProfileEmailsViewModel profileEmailModel = ViewModelProviders.of(this).get(ProfileEmailsViewModel.class);
ProfileEmailsViewModel profileEmailModel = new ViewModelProvider(this).get(ProfileEmailsViewModel.class);
profileEmailModel.getEmailsList(instanceUrl, instanceToken).observe(this, new Observer<List<Emails>>() {
@Override

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -108,7 +108,7 @@ public class ProfileFollowersFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken) {
ProfileFollowersViewModel pfModel = ViewModelProviders.of(this).get(ProfileFollowersViewModel.class);
ProfileFollowersViewModel pfModel = new ViewModelProvider(this).get(ProfileFollowersViewModel.class);
pfModel.getFollowersList(instanceUrl, instanceToken).observe(this, new Observer<List<UserInfo>>() {
@Override

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -108,7 +108,7 @@ public class ProfileFollowingFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken) {
ProfileFollowingViewModel pfModel = ViewModelProviders.of(this).get(ProfileFollowingViewModel.class);
ProfileFollowingViewModel pfModel = new ViewModelProvider(this).get(ProfileFollowingViewModel.class);
pfModel.getFollowingList(instanceUrl, instanceToken).observe(this, new Observer<List<UserInfo>>() {
@Override

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -141,7 +141,7 @@ public class ReleasesFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken, String owner, String repo) {
ReleasesViewModel releasesModel = ViewModelProviders.of(this).get(ReleasesViewModel.class);
ReleasesViewModel releasesModel = new ViewModelProvider(this).get(ReleasesViewModel.class);
releasesModel.getReleasesList(instanceUrl, instanceToken, owner, repo).observe(this, new Observer<List<Releases>>() {
@Override

View File

@ -29,6 +29,8 @@ public class RepoBottomSheetFragment extends BottomSheetDialogFragment {
TextView createMilestone = v.findViewById(R.id.createNewMilestone);
TextView addCollaborator = v.findViewById(R.id.addCollaborator);
TextView createRelease = v.findViewById(R.id.createRelease);
TextView openWebRepo = v.findViewById(R.id.openWebRepo);
TextView newFile = v.findViewById(R.id.newFile);
createLabel.setOnClickListener(new View.OnClickListener() {
@Override
@ -70,6 +72,22 @@ public class RepoBottomSheetFragment extends BottomSheetDialogFragment {
}
});
openWebRepo.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
bmListener.onButtonClicked("openWebRepo");
dismiss();
}
});
newFile.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
bmListener.onButtonClicked("newFile");
dismiss();
}
});
return v;
}

View File

@ -1,7 +1,6 @@
package org.mian.gitnex.fragments;
import android.content.Context;
import android.graphics.Color;
import android.net.Uri;
import android.os.Bundle;
import androidx.annotation.NonNull;
@ -15,7 +14,6 @@ import ru.noties.markwon.core.CorePlugin;
import ru.noties.markwon.core.MarkwonTheme;
import ru.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import ru.noties.markwon.ext.tables.TablePlugin;
import ru.noties.markwon.ext.tables.TableTheme;
import ru.noties.markwon.ext.tasklist.TaskListPlugin;
import ru.noties.markwon.html.HtmlPlugin;
import ru.noties.markwon.image.ImagesPlugin;
@ -220,6 +218,8 @@ public class RepoInfoFragment extends Fragment {
UserRepositories repoInfo = response.body();
if (isAdded()) {
if (response.isSuccessful()) {
if (response.code() == 200) {
@ -270,6 +270,8 @@ public class RepoInfoFragment extends Fragment {
}
}
@Override
public void onFailure(@NonNull Call<UserRepositories> call, @NonNull Throwable t) {
Log.e("onFailure", t.toString());
@ -292,6 +294,8 @@ public class RepoInfoFragment extends Fragment {
@Override
public void onResponse(@NonNull Call<String> call, @NonNull retrofit2.Response<String> response) {
if (isAdded()) {
if (response.code() == 200) {
final Markwon markwon = Markwon.builder(Objects.requireNonNull(getContext()))
@ -320,31 +324,29 @@ public class RepoInfoFragment extends Fragment {
}
repoFileContents.setText(bodyWithMD);
}
else if(response.code() == 401) {
} 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));
}
else if(response.code() == 403) {
} else if (response.code() == 403) {
Toasty.info(ctx, ctx.getString(R.string.authorizeError));
}
else if(response.code() == 404) {
} else if (response.code() == 404) {
fileContentsFrameHeader.setVisibility(View.GONE);
fileContentsFrame.setVisibility(View.GONE);
}
else {
} else {
Toasty.info(getContext(), getString(R.string.genericError));
}
}
}

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -123,7 +123,7 @@ public class RepositoriesByOrgFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken, String owner) {
RepositoriesByOrgViewModel orgRepoModel = ViewModelProviders.of(this).get(RepositoriesByOrgViewModel.class);
RepositoriesByOrgViewModel orgRepoModel = new ViewModelProvider(this).get(RepositoriesByOrgViewModel.class);
orgRepoModel.getRepositoriesByOrg(instanceUrl, instanceToken, owner).observe(this, new Observer<List<UserRepositories>>() {
@Override
@ -168,7 +168,9 @@ public class RepositoriesByOrgFragment extends Fragment {
@Override
public boolean onQueryTextChange(String newText) {
if(mRecyclerView.getAdapter() != null) {
adapter.getFilter().filter(newText);
}
return false;
}
});

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -144,7 +144,7 @@ public class RepositoriesFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken) {
RepositoriesListViewModel repoModel = ViewModelProviders.of(this).get(RepositoriesListViewModel.class);
RepositoriesListViewModel repoModel = new ViewModelProvider(this).get(RepositoriesListViewModel.class);
repoModel.getUserRepositories(instanceUrl, instanceToken).observe(this, new Observer<List<UserRepositories>>() {
@Override
@ -189,7 +189,9 @@ public class RepositoriesFragment extends Fragment {
@Override
public boolean onQueryTextChange(String newText) {
if(mRecyclerView.getAdapter() != null) {
adapter.getFilter().filter(newText);
}
return false;
}
});

View File

@ -185,10 +185,6 @@ public class SettingsFragment extends Fragment {
tinyDb.putInt("codeBlockId", i);
switch (codeBlockList[i]) {
case "Green - Black":
tinyDb.putInt("codeBlockColor", getResources().getColor(R.color.colorLightGreen));
tinyDb.putInt("codeBlockBackground", getResources().getColor(R.color.black));
break;
case "White - Black":
tinyDb.putInt("codeBlockColor", getResources().getColor(R.color.white));
tinyDb.putInt("codeBlockBackground", getResources().getColor(R.color.black));
@ -248,9 +244,6 @@ public class SettingsFragment extends Fragment {
tinyDb.putInt("langId", i);
switch (langList[i]) {
case "English":
tinyDb.putString("locale", "en");
break;
case "French":
tinyDb.putString("locale", "fr");
break;
@ -309,16 +302,10 @@ public class SettingsFragment extends Fragment {
tinyDb.putString("timeStr", timeList[i]);
tinyDb.putInt("timeId", i);
switch (timeList[i]) {
case "Pretty":
tinyDb.putString("dateFormat", "pretty");
break;
case "Normal":
if ("Normal".equals(timeList[i])) {
tinyDb.putString("dateFormat", "normal");
break;
default:
} else {
tinyDb.putString("dateFormat", "pretty");
break;
}
dialogInterfaceTime.dismiss();

View File

@ -7,7 +7,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -166,7 +166,7 @@ public class StarredRepositoriesFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken) {
StarredRepositoriesViewModel starredRepoModel = ViewModelProviders.of(this).get(StarredRepositoriesViewModel.class);
StarredRepositoriesViewModel starredRepoModel = new ViewModelProvider(this).get(StarredRepositoriesViewModel.class);
starredRepoModel.getUserStarredRepositories(instanceUrl, instanceToken).observe(this, new Observer<List<UserRepositories>>() {
@Override
@ -211,7 +211,9 @@ public class StarredRepositoriesFragment extends Fragment {
@Override
public boolean onQueryTextChange(String newText) {
if(mRecyclerView.getAdapter() != null) {
adapter.getFilter().filter(newText);
}
return false;
}
});

View File

@ -6,7 +6,7 @@ import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.fragment.app.Fragment;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProviders;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.DividerItemDecoration;
import androidx.recyclerview.widget.LinearLayoutManager;
import androidx.recyclerview.widget.RecyclerView;
@ -124,7 +124,7 @@ public class TeamsByOrgFragment extends Fragment {
private void fetchDataAsync(String instanceUrl, String instanceToken, String owner) {
TeamsByOrgViewModel teamModel = ViewModelProviders.of(this).get(TeamsByOrgViewModel.class);
TeamsByOrgViewModel teamModel = new ViewModelProvider(this).get(TeamsByOrgViewModel.class);
teamModel.getTeamsByOrg(instanceUrl, instanceToken, owner).observe(this, new Observer<List<Teams>>() {
@Override
@ -169,7 +169,9 @@ public class TeamsByOrgFragment extends Fragment {
@Override
public boolean onQueryTextChange(String newText) {
if(mRecyclerView.getAdapter() != null) {
adapter.getFilter().filter(newText);
}
return false;
}
});

View File

@ -3,6 +3,7 @@ package org.mian.gitnex.interfaces;
import com.google.gson.JsonElement;
import org.mian.gitnex.models.AddEmail;
import org.mian.gitnex.models.Branches;
import org.mian.gitnex.models.NewFile;
import org.mian.gitnex.models.UpdateIssueAssignee;
import org.mian.gitnex.models.UpdateIssueState;
import org.mian.gitnex.models.Collaborators;
@ -204,4 +205,13 @@ public interface ApiInterface {
@GET("admin/users") // get all users
Call<List<UserInfo>> adminGetUsers(@Header("Authorization") String token);
@GET("repos/{owner}/{repo}/stargazers") // get all repo stars
Call<List<UserInfo>> getRepoStargazers(@Header("Authorization") String token, @Path("owner") String ownerName, @Path("repo") String repoName);
@GET("repos/{owner}/{repo}/subscribers") // get all repo watchers
Call<List<UserInfo>> getRepoWatchers(@Header("Authorization") String token, @Path("owner") String ownerName, @Path("repo") String repoName);
@POST("repos/{owner}/{repo}/contents/{file}") // create new file
Call<JsonElement> createNewFile(@Header("Authorization") String token, @Path("owner") String ownerName, @Path("repo") String repoName, @Path("file") String fileName, @Body NewFile jsonStr);
}

View File

@ -0,0 +1,99 @@
package org.mian.gitnex.models;
/**
* Author M M Arif
*/
public class NewFile {
private String branch;
private String content;
private String message;
private String new_branch;
private authorObject author;
private committerObject committer;
public String getBranch() {
return branch;
}
public void setBranch(String branch) {
this.branch = branch;
}
public String getContents() {
return content;
}
public void setContents(String contents) {
this.content = contents;
}
public String getMessage() {
return message;
}
public void setMessage(String message) {
this.message = message;
}
public String getNew_branch() {
return new_branch;
}
public void setNew_branch(String new_branch) {
this.new_branch = new_branch;
}
public class authorObject {
private String email;
private String name;
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
public class committerObject {
private String email;
private String name;
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
}
public NewFile(String branch, String content, String message, String new_branch) {
this.branch = branch;
this.content = content;
this.message = message;
this.new_branch = new_branch;
}
}

View File

@ -7,9 +7,11 @@ import android.content.res.Configuration;
import android.content.res.Resources;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;
import android.util.Base64;
import android.util.DisplayMetrics;
import java.net.HttpURLConnection;
import java.net.URL;
import java.nio.charset.StandardCharsets;
import java.text.DecimalFormat;
import java.util.Calendar;
import java.util.Locale;
@ -77,6 +79,10 @@ public class AppUtil {
return str.matches("^[\\w.-]+$");
}
public Boolean checkStringsWithDash(String str) { // [a-zA-Z0-9-_. ]
return str.matches("^[\\w-]+$");
}
public Boolean checkIntegers(String str) {
return str.matches("\\d+");
}
@ -180,4 +186,28 @@ public class AppUtil {
}
public String encodeBase64(String str) {
String base64Str = str;
if(!str.equals("")) {
byte[] data = str.getBytes(StandardCharsets.UTF_8);
base64Str = Base64.encodeToString(data, Base64.DEFAULT);
}
return base64Str;
}
public String decodeBase64(String str) {
String base64Str = str;
if(!str.equals("")) {
byte[] data = Base64.decode(base64Str, Base64.DEFAULT);
base64Str = new String(data, StandardCharsets.UTF_8);
}
return base64Str;
}
}

View File

@ -0,0 +1,60 @@
package org.mian.gitnex.viewmodels;
import android.util.Log;
import androidx.annotation.NonNull;
import androidx.lifecycle.LiveData;
import androidx.lifecycle.MutableLiveData;
import androidx.lifecycle.ViewModel;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.models.UserInfo;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
/**
* Author M M Arif
*/
public class RepoStargazersViewModel extends ViewModel {
private static MutableLiveData<List<UserInfo>> stargazersList;
public LiveData<List<UserInfo>> getRepoStargazers(String instanceUrl, String token, String repoOwner, String repoName) {
stargazersList = new MutableLiveData<>();
loadRepoStargazers(instanceUrl, token, repoOwner, repoName);
return stargazersList;
}
public static void loadRepoStargazers(String instanceUrl, String token, String repoOwner, String repoName) {
Call<List<UserInfo>> call = RetrofitClient
.getInstance(instanceUrl)
.getApiInterface()
.getRepoStargazers(token, repoOwner, repoName);
call.enqueue(new Callback<List<UserInfo>>() {
@Override
public void onResponse(@NonNull Call<List<UserInfo>> call, @NonNull Response<List<UserInfo>> response) {
if(response.isSuccessful()) {
if(response.code() == 200) {
stargazersList.postValue(response.body());
}
}
}
@Override
public void onFailure(@NonNull Call<List<UserInfo>> call, Throwable t) {
Log.i("onFailure", t.toString());
}
});
}
}

View File

@ -0,0 +1,60 @@
package org.mian.gitnex.viewmodels;
import android.util.Log;
import androidx.annotation.NonNull;
import androidx.lifecycle.LiveData;
import androidx.lifecycle.MutableLiveData;
import androidx.lifecycle.ViewModel;
import org.mian.gitnex.clients.RetrofitClient;
import org.mian.gitnex.models.UserInfo;
import java.util.List;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
/**
* Author M M Arif
*/
public class RepoWatchersViewModel extends ViewModel {
private static MutableLiveData<List<UserInfo>> watchersList;
public LiveData<List<UserInfo>> getRepoWatchers(String instanceUrl, String token, String repoOwner, String repoName) {
watchersList = new MutableLiveData<>();
loadRepoWatchers(instanceUrl, token, repoOwner, repoName);
return watchersList;
}
public static void loadRepoWatchers(String instanceUrl, String token, String repoOwner, String repoName) {
Call<List<UserInfo>> call = RetrofitClient
.getInstance(instanceUrl)
.getApiInterface()
.getRepoWatchers(token, repoOwner, repoName);
call.enqueue(new Callback<List<UserInfo>>() {
@Override
public void onResponse(@NonNull Call<List<UserInfo>> call, @NonNull Response<List<UserInfo>> response) {
if(response.isSuccessful()) {
if(response.code() == 200) {
watchersList.postValue(response.body());
}
}
}
@Override
public void onFailure(@NonNull Call<List<UserInfo>> call, Throwable t) {
Log.i("onFailure", t.toString());
}
});
}
}

View File

@ -0,0 +1,5 @@
<vector android:height="24dp" android:tint="#FFFFFF"
android:viewportHeight="24.0" android:viewportWidth="24.0"
android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
<path android:fillColor="#FF000000" android:pathData="M6,2c-1.1,0 -1.99,0.9 -1.99,2L4,20c0,1.1 0.89,2 1.99,2L18,22c1.1,0 2,-0.9 2,-2L20,8l-6,-6L6,2zM13,9L13,3.5L18.5,9L13,9z"/>
</vector>

View File

@ -0,0 +1,5 @@
<vector android:height="24dp" android:tint="#FFFFFF"
android:viewportHeight="24.0" android:viewportWidth="24.0"
android:width="24dp" xmlns:android="http://schemas.android.com/apk/res/android">
<path android:fillColor="#FF000000" android:pathData="M19,4L5,4c-1.11,0 -2,0.9 -2,2v12c0,1.1 0.89,2 2,2h4v-2L5,18L5,8h14v10h-4v2h4c1.1,0 2,-0.9 2,-2L21,6c0,-1.1 -0.89,-2 -2,-2zM12,10l-4,4h3v6h2v-6h3l-4,-4z"/>
</vector>

View File

@ -10,7 +10,6 @@
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/toolbar"
android:layout_width="match_parent"
@ -72,7 +71,7 @@
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -10,8 +10,6 @@
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"

View File

@ -11,8 +11,6 @@
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
@ -44,10 +42,8 @@
</com.google.android.material.appbar.AppBarLayout>
<ScrollView
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:android="http://schemas.android.com/apk/res/android"
android:background="@color/backgroundColor">
<LinearLayout

View File

@ -11,8 +11,6 @@
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
@ -44,10 +42,8 @@
</com.google.android.material.appbar.AppBarLayout>
<ScrollView
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:android="http://schemas.android.com/apk/res/android"
android:background="@color/backgroundColor">
<LinearLayout

View File

@ -10,8 +10,6 @@
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
@ -43,10 +41,8 @@
</com.google.android.material.appbar.AppBarLayout>
<ScrollView
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:android="http://schemas.android.com/apk/res/android"
android:background="@color/backgroundColor">
<LinearLayout

View File

@ -8,7 +8,6 @@
android:gravity="center">
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical"
@ -62,7 +61,6 @@
android:padding="10dp"
android:textSize="14sp"
tools:ignore="Autofill"
android:labelFor="@+id/instance_url"
android:background="@drawable/shape_inputs"
android:drawableStart="@drawable/ic_link_24dp"
android:drawablePadding="10dp"
@ -80,7 +78,6 @@
android:padding="10dp"
android:textSize="14sp"
tools:ignore="Autofill"
android:labelFor="@+id/login_uid"
android:background="@drawable/shape_inputs"
android:drawableStart="@drawable/ic_person_24dp"
android:drawablePadding="10dp"
@ -98,7 +95,6 @@
android:padding="10dp"
android:textSize="14sp"
tools:ignore="Autofill"
android:labelFor="@+id/login_passwd"
android:background="@drawable/shape_inputs"
android:drawableStart="@drawable/ic_lock_24dp"
android:drawablePadding="10dp"
@ -116,7 +112,6 @@
android:padding="10dp"
android:textSize="14sp"
tools:ignore="Autofill"
android:labelFor="@+id/otpCode"
android:background="@drawable/shape_inputs"
android:drawableStart="@drawable/ic_otp"
android:drawablePadding="10dp"

View File

@ -0,0 +1,229 @@
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
xmlns:android="http://schemas.android.com/apk/res/android"
android:background="@color/colorPrimary">
<com.google.android.material.appbar.AppBarLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?attr/colorPrimary"
tools:ignore="UnusedAttribute">
<ImageView
android:id="@+id/close"
android:layout_width="30dp"
android:layout_height="30dp"
android:layout_marginRight="15dp"
android:layout_marginLeft="15dp"
android:gravity="center_vertical"
android:contentDescription="@string/close"
android:src="@drawable/ic_close" />
<TextView
android:id="@+id/toolbar_title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:text="@string/pageTitleNewFile"
android:textColor="@color/white"
android:maxLines="1"
android:textSize="20sp" />
</androidx.appcompat.widget.Toolbar>
</com.google.android.material.appbar.AppBarLayout>
<ScrollView
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/backgroundColor">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="20dp"
android:paddingBottom="30dp"
android:orientation="vertical">
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/newFileNameTintCopy"
android:textColor="@color/colorWhite"
android:textSize="16sp" />
<EditText
android:id="@+id/newFileName"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="10dp"
android:padding="10dp"
android:textSize="14sp"
tools:ignore="Autofill"
android:labelFor="@+id/newFileName"
android:background="@drawable/shape_inputs"
android:textColor="@color/colorWhite"
android:textColorHint="@color/colorWhite"
android:inputType="textCapSentences|text"
android:textColorHighlight="@color/colorWhite"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/newFileNameHintMessage"
android:textColor="@color/hintColor"
android:textSize="12sp"
android:paddingStart="10dp"
android:paddingEnd="5dp"
android:gravity="end" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/newFileContentTintCopy"
android:textColor="@color/colorWhite"
android:textSize="16sp"
android:layout_marginTop="10dp" />
<EditText
android:id="@+id/newFileContent"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="10dp"
android:padding="10dp"
android:background="@drawable/shape_inputs"
android:maxLines="16"
android:minLines="14"
tools:ignore="Autofill"
android:labelFor="@+id/newFileContent"
android:scrollbars="vertical"
android:gravity="top|start"
android:textSize="14sp"
android:textColor="@color/colorWhite"
android:textColorHint="@color/colorWhite"
android:inputType="textCapSentences|textMultiLine"
android:textColorHighlight="@color/colorWhite"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/newFileOldBranches"
android:textColor="@color/colorWhite"
android:textSize="16sp"
android:layout_marginTop="10dp"/>
<Spinner
android:id="@+id/newFileBranchesSpinner"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:spinnerMode="dropdown"
android:layout_marginTop="10dp"
android:layout_marginBottom="10dp"
android:paddingLeft="5dp"
android:paddingRight="5dp"
android:paddingStart="5dp" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/newFileCurrentBranchMessage"
android:textColor="@color/hintColor"
android:textSize="12sp"
android:paddingStart="10dp"
android:paddingEnd="5dp"
android:gravity="end" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/newFileBranchTintCopy"
android:textColor="@color/colorWhite"
android:textSize="16sp"
android:layout_marginTop="10dp" />
<EditText
android:id="@+id/newFileBranchName"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="10dp"
android:padding="10dp"
android:textSize="14sp"
tools:ignore="Autofill"
android:labelFor="@+id/newFileBranchName"
android:background="@drawable/shape_inputs"
android:textColor="@color/colorWhite"
android:textColorHint="@color/colorWhite"
android:inputType="textCapSentences|text"
android:textColorHighlight="@color/colorWhite"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/newFileNewBranchMessage"
android:textColor="@color/hintColor"
android:textSize="12sp"
android:paddingStart="10dp"
android:paddingEnd="5dp"
android:gravity="end" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/newFileMessageTintCopy"
android:textColor="@color/colorWhite"
android:textSize="16sp"
android:layout_marginTop="10dp" />
<EditText
android:id="@+id/newFileCommitMessage"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="10dp"
android:padding="10dp"
android:textSize="14sp"
tools:ignore="Autofill"
android:labelFor="@+id/newFileCommitMessage"
android:background="@drawable/shape_inputs"
android:textColor="@color/colorWhite"
android:textColorHint="@color/colorWhite"
android:inputType="textCapSentences|text"
android:textColorHighlight="@color/colorWhite"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/characters255Limit"
android:textColor="@color/hintColor"
android:textSize="12sp"
android:paddingStart="10dp"
android:paddingEnd="5dp"
android:gravity="end" />
<Button
android:id="@+id/newFileCreate"
android:gravity="center"
android:layout_gravity="end"
android:layout_marginTop="20dp"
android:layout_width="wrap_content"
android:layout_height="40dp"
android:width="140dp"
android:text="@string/newFileButtonCopy"
android:background="@drawable/shape_buttons"
android:textColor="@color/btnTextColor" />
</LinearLayout>
</ScrollView>
</LinearLayout>

View File

@ -12,7 +12,6 @@
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/toolbar"
android:layout_width="match_parent"
@ -48,7 +47,6 @@
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:android="http://schemas.android.com/apk/res/android"
android:background="@color/backgroundColor">
<LinearLayout

View File

@ -10,8 +10,6 @@
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"

View File

@ -0,0 +1,73 @@
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/colorPrimary"
android:orientation="vertical">
<com.google.android.material.appbar.AppBarLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?attr/colorPrimary"
tools:ignore="UnusedAttribute">
<ImageView
android:id="@+id/close"
android:layout_width="30dp"
android:layout_height="30dp"
android:layout_marginRight="15dp"
android:layout_marginLeft="15dp"
android:gravity="center_vertical"
android:contentDescription="@string/close"
android:src="@drawable/ic_close" />
<TextView
android:id="@+id/toolbar_title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:textColor="@color/white"
android:maxLines="1"
android:textSize="20sp" />
</androidx.appcompat.widget.Toolbar>
</com.google.android.material.appbar.AppBarLayout>
<GridView
android:id="@+id/gridView"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:horizontalSpacing="10dp"
android:numColumns="4"
android:columnWidth="80dp"
android:stretchMode="columnWidth"
android:gravity="center"/>
<TextView
android:id="@+id/noDataStargazers"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_margin="15dp"
android:gravity="center"
android:text="@string/noDataFound"
android:textColor="@color/white"
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:indeterminate="true"
android:visibility="visible" />
</LinearLayout>

View File

@ -0,0 +1,73 @@
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/colorPrimary"
android:orientation="vertical">
<com.google.android.material.appbar.AppBarLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?attr/colorPrimary"
tools:ignore="UnusedAttribute">
<ImageView
android:id="@+id/close"
android:layout_width="30dp"
android:layout_height="30dp"
android:layout_marginRight="15dp"
android:layout_marginLeft="15dp"
android:gravity="center_vertical"
android:contentDescription="@string/close"
android:src="@drawable/ic_close" />
<TextView
android:id="@+id/toolbar_title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:textColor="@color/white"
android:maxLines="1"
android:textSize="20sp" />
</androidx.appcompat.widget.Toolbar>
</com.google.android.material.appbar.AppBarLayout>
<GridView
android:id="@+id/gridView"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="10dp"
android:horizontalSpacing="10dp"
android:numColumns="4"
android:columnWidth="80dp"
android:stretchMode="columnWidth"
android:gravity="center"/>
<TextView
android:id="@+id/noDataWatchers"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_margin="15dp"
android:gravity="center"
android:text="@string/noDataFound"
android:textColor="@color/white"
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:indeterminate="true"
android:visibility="visible" />
</LinearLayout>

View File

@ -10,8 +10,6 @@
android:layout_height="wrap_content">
<androidx.appcompat.widget.Toolbar
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/toolbar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
@ -44,7 +42,6 @@
<ScrollView android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:android="http://schemas.android.com/apk/res/android"
android:background="@color/backgroundColor">
<LinearLayout
@ -76,6 +73,18 @@
android:text="@string/liberaPaySponsorsFabian"
android:textColor="@color/white"
android:textSize="16sp"
android:layout_marginBottom="10dp"
android:textColorLink="@color/lightBlue"
/>
<TextView
android:id="@+id/liberaPaySponsorsThomas"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/liberaPaySponsorsThomas"
android:textColor="@color/white"
android:textSize="16sp"
android:layout_marginBottom="10dp"
android:textColorLink="@color/lightBlue"
/>

View File

@ -6,14 +6,12 @@
android:id="@+id/relativeLayoutMainFrame"
android:background="@color/backgroundColor">
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingStart="15dp"
android:paddingEnd="15dp"
android:paddingTop="10dp"
android:paddingBottom="15dp"
android:paddingBottom="5dp"
android:id="@+id/branchesFrame"
android:layout_margin="15dp"
android:orientation="vertical">
<TextView
@ -38,10 +36,8 @@
android:layout_marginTop="10dp"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:textIsSelectable="true"
android:textColor="@color/colorWhite"
android:textSize="16sp"
android:autoLink="web"
android:textColorLink="@color/lightBlue"/>
</LinearLayout>

View File

@ -27,7 +27,7 @@
android:theme="@style/ThemeOverlay.AppCompat.Dark"
android:queryHint="Search" />
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
<LinearLayout
android:id="@+id/select_all_container"
android:visibility="gone"
android:layout_width="match_parent"

View File

@ -20,7 +20,7 @@
android:scrollbars="vertical"
/>
<GridView xmlns:android="http://schemas.android.com/apk/res/android"
<GridView
android:id="@+id/gridView"
android:numColumns="auto_fit"
android:gravity="center"
@ -42,7 +42,7 @@
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -25,6 +25,15 @@
android:text="@string/noDataCollaboratorTab"
android:textColor="@color/white"
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_centerInParent="true"
android:indeterminate="true"
android:visibility="visible" />
</RelativeLayout>

View File

@ -22,7 +22,7 @@
</androidx.swiperefreshlayout.widget.SwipeRefreshLayout>
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_barClosed"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -33,7 +33,7 @@
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -33,7 +33,7 @@
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -20,7 +20,7 @@
</androidx.swiperefreshlayout.widget.SwipeRefreshLayout>
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -5,7 +5,6 @@
android:layout_height="match_parent">
<ScrollView
xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:background="@color/backgroundColor"
android:layout_width="match_parent"
@ -113,7 +112,7 @@
android:indeterminate="true"
android:visibility="visible"
android:layout_centerInParent="true"
xmlns:android="http://schemas.android.com/apk/res/android" />
/>
</RelativeLayout>

View File

@ -19,7 +19,7 @@
</androidx.swiperefreshlayout.widget.SwipeRefreshLayout>
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -33,7 +33,7 @@
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -107,6 +107,7 @@
android:textIsSelectable="true"
android:textSize="16sp"
android:paddingTop="5dp"
android:autoLink="web"
android:textColor="@color/colorWhite"/>
<TextView
@ -328,7 +329,7 @@
android:indeterminate="true"
android:visibility="visible"
android:layout_centerInParent="true"
xmlns:android="http://schemas.android.com/apk/res/android" />
/>
</RelativeLayout>

View File

@ -32,7 +32,7 @@
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -32,7 +32,7 @@
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -7,7 +7,6 @@
<ScrollView
android:layout_width="match_parent"
android:layout_height="match_parent"
xmlns:android="http://schemas.android.com/apk/res/android"
android:background="@color/backgroundColor" >
<RelativeLayout

View File

@ -32,7 +32,7 @@
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -32,7 +32,7 @@
android:textSize="20sp"
android:visibility="gone" />
<ProgressBar xmlns:android="http://schemas.android.com/apk/res/android"
<ProgressBar
android:id="@+id/progress_bar"
style="@style/Base.Widget.AppCompat.ProgressBar"
android:layout_width="match_parent"

View File

@ -6,10 +6,10 @@
android:id="@+id/relativeLayoutMainFrame"
android:background="@color/backgroundColor">
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="15dp"
android:layout_margin="15dp"
android:id="@+id/labelsFrame"
android:orientation="horizontal">

View File

@ -6,10 +6,10 @@
android:id="@+id/relativeLayoutMainFrame"
android:background="@color/backgroundColor">
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="15dp"
android:layout_margin="15dp"
android:id="@+id/milestoneFrame"
android:orientation="vertical">

View File

@ -4,7 +4,7 @@
android:layout_height="wrap_content"
android:background="@color/backgroundColor" >
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
<RelativeLayout
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/linearLayoutFrame"
android:layout_width="match_parent"
@ -85,13 +85,28 @@
android:layout_marginBottom="8dp"
android:orientation="horizontal">
<TextView
android:id="@+id/repoOpenIssuesCountMy"
android:layout_width="0dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_issue_comments"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="16sp" />
<TextView
android:id="@+id/repoStarsMy"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_star"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoStars"
android:textColor="@color/colorWhite"
android:textSize="16sp" />
@ -99,30 +114,25 @@
<TextView
android:id="@+id/repoWatchersMy"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_watchers"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="16sp" />
<TextView
android:id="@+id/repoOpenIssuesCountMy"
<ImageView
android:id="@+id/reposDropdownMenu"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_comment"
android:drawablePadding="06dp"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="16sp" />
<TextView
android:id="@+id/repoSpace"
android:layout_width="wrap_content"
android:layout_weight=".10"
android:layout_height="wrap_content"
android:layout_weight=".25" />
android:layout_gravity="end"
android:scaleType="fitEnd"
android:src="@drawable/ic_dotted_menu_horizontal"
android:contentDescription="@string/menuContentDesc" />
</LinearLayout>

View File

@ -32,7 +32,6 @@
android:paddingEnd="5dp" />
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="horizontal"
android:layout_width="match_parent"
android:layout_height="wrap_content"

View File

@ -5,7 +5,7 @@
android:layout_height="wrap_content"
android:background="@color/backgroundColor" >
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
<RelativeLayout
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/linearLayoutFrame"
android:layout_width="match_parent"

View File

@ -4,14 +4,14 @@
android:layout_height="wrap_content"
android:background="@color/backgroundColor" >
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
<LinearLayout
android:id="@+id/linearLayoutFrame"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_alignParentTop="true"
android:fitsSystemWindows="true"
android:orientation="vertical"
android:padding="15dp"
android:layout_margin="15dp"
android:theme="@style/AppTheme">
<LinearLayout
@ -83,10 +83,8 @@
android:layout_height="wrap_content"
android:layout_marginTop="5dp"
android:text="@string/releaseZip"
android:textIsSelectable="true"
android:textColor="@color/colorWhite"
android:textSize="16sp"
android:autoLink="web"
android:textColorLink="@color/lightBlue"/>
<TextView
@ -94,11 +92,9 @@
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/releaseTar"
android:textIsSelectable="true"
android:layout_marginTop="5dp"
android:textColor="@color/colorWhite"
android:textSize="16sp"
android:autoLink="web"
android:textColorLink="@color/lightBlue"/>
</LinearLayout>

View File

@ -7,6 +7,18 @@
android:background="@color/backgroundColor"
android:paddingTop="8dp">
<TextView
android:id="@+id/newFile"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:text="@string/pageTitleNewFile"
android:drawableStart="@drawable/ic_file"
android:drawablePadding="24dp"
android:textColor="@color/white"
android:textSize="16sp"
android:padding="16dp" />
<TextView
android:id="@+id/createNewIssue"
android:layout_width="match_parent"
@ -67,4 +79,16 @@
android:textSize="16sp"
android:padding="16dp" />
<TextView
android:id="@+id/openWebRepo"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical"
android:drawableStart="@drawable/ic_open_in_browser"
android:drawablePadding="24dp"
android:padding="16dp"
android:text="@string/openWebRepo"
android:textColor="@color/white"
android:textSize="16sp" />
</LinearLayout>

View File

@ -6,12 +6,12 @@
android:id="@+id/relativeLayoutMainFrame"
android:background="@color/backgroundColor">
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
<RelativeLayout
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/relativeLayoutFrame"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="15dp"
android:layout_margin="15dp"
android:theme="@style/AppTheme"
tools:context=".activities.RepoDetailActivity">
@ -38,7 +38,7 @@
android:height="16dp"
android:layout_marginEnd="15dp"
android:layout_below="@+id/assigneeAvatar"
android:drawableTop="@drawable/ic_issue_comments"
android:drawableTop="@drawable/ic_comment"
android:gravity="center"
android:textColor="@color/colorWhite"
android:textSize="14sp" />

View File

@ -0,0 +1,27 @@
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/gridViewData"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@color/colorPrimary"
android:orientation="vertical">
<ImageView
android:id="@+id/memberAvatar"
android:layout_width="match_parent"
android:layout_height="110dp"
android:contentDescription="@string/starMember"
android:src="@drawable/ic_person_filled" />
<TextView
android:id="@+id/memberName"
android:layout_width="match_parent"
android:layout_height="60dp"
android:gravity="top|center_horizontal"
android:layout_marginTop="1dp"
android:text="@string/starMember"
android:textSize="14sp"
android:textColor="@color/white" />
</LinearLayout>

View File

@ -0,0 +1,27 @@
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/gridViewData"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="@color/colorPrimary"
android:orientation="vertical">
<ImageView
android:id="@+id/memberAvatar"
android:layout_width="match_parent"
android:layout_height="110dp"
android:contentDescription="@string/watcherMember"
android:src="@drawable/ic_person_filled" />
<TextView
android:id="@+id/memberName"
android:layout_width="match_parent"
android:layout_height="60dp"
android:gravity="top|center_horizontal"
android:layout_marginTop="1dp"
android:text="@string/watcherMember"
android:textSize="14sp"
android:textColor="@color/white" />
</LinearLayout>

View File

@ -4,7 +4,7 @@
android:layout_height="wrap_content"
android:background="@color/backgroundColor" >
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
<RelativeLayout
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/linearLayoutFrame"
android:layout_width="match_parent"
@ -85,13 +85,28 @@
android:layout_marginBottom="8dp"
android:orientation="horizontal">
<TextView
android:id="@+id/repoOpenIssuesCount"
android:layout_width="0dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_issue_comments"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
<TextView
android:id="@+id/repoStars"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_star"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoStars"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
@ -99,30 +114,25 @@
<TextView
android:id="@+id/repoWatchers"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_watchers"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
<TextView
android:id="@+id/repoOpenIssuesCount"
<ImageView
android:id="@+id/reposDropdownMenu"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_comment"
android:drawablePadding="06dp"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
<TextView
android:id="@+id/repoSpace"
android:layout_width="wrap_content"
android:layout_weight=".10"
android:layout_height="wrap_content"
android:layout_weight=".25" />
android:layout_gravity="end"
android:scaleType="fitEnd"
android:src="@drawable/ic_dotted_menu_horizontal"
android:contentDescription="@string/menuContentDesc" />
</LinearLayout>

View File

@ -4,7 +4,7 @@
android:layout_height="wrap_content"
android:background="@color/backgroundColor" >
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
<RelativeLayout
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/linearLayoutFrame"
android:layout_width="match_parent"
@ -85,13 +85,28 @@
android:layout_marginBottom="8dp"
android:orientation="horizontal">
<TextView
android:id="@+id/repoOpenIssuesCount"
android:layout_width="0dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_issue_comments"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
<TextView
android:id="@+id/repoStars"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_star"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoStars"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
@ -99,30 +114,25 @@
<TextView
android:id="@+id/repoWatchers"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_watchers"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
<TextView
android:id="@+id/repoOpenIssuesCount"
<ImageView
android:id="@+id/reposDropdownMenu"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_comment"
android:drawablePadding="06dp"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
<TextView
android:id="@+id/repoSpace"
android:layout_width="wrap_content"
android:layout_weight=".10"
android:layout_height="wrap_content"
android:layout_weight=".25" />
android:layout_gravity="end"
android:scaleType="fitEnd"
android:src="@drawable/ic_dotted_menu_horizontal"
android:contentDescription="@string/menuContentDesc" />
</LinearLayout>

View File

@ -4,7 +4,7 @@
android:layout_height="wrap_content"
android:background="@color/backgroundColor" >
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
<RelativeLayout
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/linearLayoutFrame"
android:layout_width="match_parent"
@ -85,13 +85,28 @@
android:layout_marginBottom="8dp"
android:orientation="horizontal">
<TextView
android:id="@+id/repoOpenIssuesCount"
android:layout_width="0dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_issue_comments"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
<TextView
android:id="@+id/repoStars"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_star"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoStars"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
@ -99,30 +114,25 @@
<TextView
android:id="@+id/repoWatchers"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_height="20dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_watchers"
android:drawablePadding="6dp"
android:gravity="center_vertical"
android:layout_gravity="center_vertical"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
<TextView
android:id="@+id/repoOpenIssuesCount"
<ImageView
android:id="@+id/reposDropdownMenu"
android:layout_width="0dp"
android:layout_height="24dp"
android:layout_weight=".25"
android:drawableStart="@drawable/ic_comment"
android:drawablePadding="06dp"
android:text="@string/repoWatchers"
android:textColor="@color/colorWhite"
android:textSize="14sp" />
<TextView
android:id="@+id/repoSpace"
android:layout_width="wrap_content"
android:layout_weight=".10"
android:layout_height="wrap_content"
android:layout_weight=".25" />
android:layout_gravity="end"
android:scaleType="fitEnd"
android:src="@drawable/ic_dotted_menu_horizontal"
android:contentDescription="@string/menuContentDesc" />
</LinearLayout>

View File

@ -6,7 +6,7 @@
android:id="@+id/relativeLayoutMainFrame"
android:background="@color/backgroundColor">
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
<LinearLayout
android:layout_width="match_parent"
android:layout_height="match_parent"
android:padding="15dp"

View File

@ -0,0 +1,19 @@
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
<item
android:id="@+id/repoOpenInBrowser"
android:icon="@drawable/ic_open_in_browser"
android:title="@string/openWebRepo" />
<item
android:id="@+id/repoStargazers"
android:icon="@drawable/ic_star"
android:title="@string/repoStargazersInMenu" />
<item
android:id="@+id/repoWatchers"
android:icon="@drawable/ic_watchers"
android:title="@string/repoWatchersInMenu" />
</menu>

View File

@ -8,7 +8,7 @@
<string name="navSettings">Einstellungen</string>
<string name="navOrgs">Organisationen</string>
<string name="navAbout">Über</string>
<string name="navRate">Rate GitNex</string>
<string name="navRate">Bewerte GitNex</string>
<string name="navLogout">Ausloggen</string>
<!-- menu items -->
@ -87,10 +87,10 @@
<string name="orgNameErrorEmpty">Organisationsname ist leer</string>
<string name="orgNameErrorInvalid">Organisationsname ist nicht gültig, [a&#8211;z A&#8211;Z 0&#8211;9 &#8211; _]</string>
<string name="orgDescError"> Die Organisationsbeschreibung überschreitet die maximale Anzahl von 255 Zeichen</string>
<string name="orgDescError">Organisationsbeschreibung überschreitet maximale Anzahl von 255 Zeichen</string>
<string name="orgCreated">Organisation erfolgreich erstellt!</string>
<string name="orgCreatedError">Etwas ist schief gelaufen. Bitte versuche es erneut</string>
<string name="orgExistsError">Organization already exists</string>
<string name="orgExistsError">Organisation existiert bereits</string>
<string name="processingText">wird bearbeitet</string>
<string name="search">Suche</string>
@ -146,7 +146,7 @@
<string name="issueStatusTextClosed">Status: geschlossen</string>
<string name="issueStatusClosed">schließen</string>
<string name="issueCreator">Ersteller:\u0020</string>
<string name="issueAssigneesText">Zugewiesene</string>
<string name="issueAssigneesText">Zuständige</string>
<string name="issueTypeIssue">Typ: Issue</string>
<string name="issueTypePullRequest">Typ: Pull Anfrage</string>
<string name="issueCommenter">Kommentator:\u0020</string>
@ -226,11 +226,11 @@
<string name="settingsTimeSelectorDialogTitle">Zeitformat auswählen</string>
<string name="settingsIssueBadgeHeaderText">Issues Badge</string>
<string name="settingsHelpTranslateText">Hilf uns dabei, GitNex in deine Sprache zu übersetzen.</string>
<string name="codeBlockHeaderText">Code Block Color</string>
<string name="settingsCodeBlockSelectorDialogTitle">Code Block Color Selector</string>
<string name="codeBlockHeaderText">Code Block Farbe</string>
<string name="settingsCodeBlockSelectorDialogTitle">Code Block Farb Auswahl</string>
<string name="settingsHomeScreenHeaderText">Home Screen</string>
<string name="settingsHomeScreenSelectedText">My Repositories</string>
<string name="settingshomeScreenSelectorDialogTitle">Select Home Screen</string>
<string name="settingsHomeScreenSelectedText">Meine Repositories</string>
<string name="settingshomeScreenSelectorDialogTitle">Home Screen Auswählen</string>
<!-- settings -->
<string name="noMoreData">Keine weiteren Daten verfügbar!</string>
@ -312,6 +312,7 @@
<string name="removeCollaboratorMessage">Möchtest du den Nutzer wirklich von dieser Repository entfernen?</string>
<string name="removeCollaboratorToastText">Benuter von der Repository entfernt.</string>
<string name="addCollaboratorToastText">Benutzer zu der Repository hinzugefügt.</string>
<string name="openWebRepo">Öfne mit Browser</string>
<!-- add collaborator -->
<!-- profile section -->
@ -337,9 +338,9 @@
<string name="reOpenIssue">Issue neu öffnen</string>
<string name="issueStateClosed">Issue geschlossen</string>
<string name="issueStateReopened">Issue neu geöffnet</string>
<string name="addRemoveAssignees2">Add Assignees</string>
<string name="addRemoveAssignees">Add / Remove Assignees</string>
<string name="assigneesUpdated">Assignees updated</string>
<string name="addRemoveAssignees2">Füge Zuständige hinzu</string>
<string name="addRemoveAssignees">Zuständige Hinzufügen / Entfernen</string>
<string name="assigneesUpdated">Zuständoge aktualisiert</string>
<!-- single issue section -->
<!-- multi select dialog -->
@ -357,7 +358,7 @@
<!-- admin -->
<string name="adminCreateNewUser">Neuen Benutzer erstellen</string>
<string name="adminUsers">Users</string>
<string name="adminUsers">Benutzer</string>
<string name="userRoleAdmin">Admin</string>
<!-- admin -->
@ -370,38 +371,65 @@
<string name="userInvalidUserName">Ungültiger Benutzername</string>
<string name="userInvalidEmail">Ungültige E-Mail</string>
<string name="userCreatedText">Neuer Benutzer erfolgreich erstellt</string>
<string name="userExistsError">User already exists</string>
<string name="userExistsError">Benutzer existiert bereits</string>
<!-- create user -->
<!-- edit issue -->
<string name="editIssueNavHeader">Edit Issue #%1$s</string>
<string name="editIssueSuccessMessage">Issue updated.</string>
<string name="editIssueNavHeader">Bearbeite Issue #%1$s</string>
<string name="editIssueSuccessMessage">Issue aktualisiert.</string>
<!-- edit issue -->
<!-- release -->
<string name="createRelease">Create Release</string>
<string name="releaseTagNameText">Tag Name</string>
<string name="releaseTitleText">Title</string>
<string name="releaseContentText">Content</string>
<string name="releaseTypeText">Mark as Pre-Release</string>
<string name="releaseBranchText">Select Branch</string>
<string name="releaseDraftText">Draft</string>
<string name="tagNameErrorEmpty">Tag name is empty</string>
<string name="titleErrorEmpty">Title is empty</string>
<string name="releaseCreatedText">New release created</string>
<string name="createRelease">Release Erstellen</string>
<string name="releaseTagNameText">Tag</string>
<string name="releaseTitleText">Titel</string>
<string name="releaseContentText">Inhalt</string>
<string name="releaseTypeText">Als Pre-Release markieren</string>
<string name="releaseBranchText">Branch auswählen</string>
<string name="releaseDraftText">Entwurf</string>
<string name="tagNameErrorEmpty">Der Tag ist leer</string>
<string name="titleErrorEmpty">Der Titel ist leer</string>
<string name="releaseCreatedText">Neuer release erstellt</string>
<!-- release -->
<string name="loginOTPError">Enter OTP code</string>
<string name="loginOTPTypeError">OTP code should be numbers.</string>
<string name="loginOTPError">Bitte gib den OTP code ein</string>
<string name="loginOTPTypeError">Der OTP code muss aus Zahlen bestehen.</string>
<string name="loginOTP">OTP Code (Optional)</string>
<string name="otpMessage">Enter the otp code if 2FA is enabled</string>
<string name="otpMessage">Gebe den otp code ein wenn 2FA eingeschaltet ist</string>
<string name="repoStargazersInMenu">Stargazers</string>
<string name="repoWatchersInMenu">Watchers</string>
<string name="noDataStargazers">No stars found</string>
<string name="noDataWatchers">No watchers found</string>
<string name="starMember">Star</string>
<string name="watcherMember">Watcher</string>
<string name="commitLinkBranchesTab">Commit</string>
<string name="zipArchiveDownloadReleasesTab">Zip Archive</string>
<string name="tarArchiveDownloadReleasesTab">Tar Archive</string>
<!-- new file -->
<string name="newFileNameTintCopy">File Name</string>
<string name="newFileBranchTintCopy">Branch Name</string>
<string name="newFileContentTintCopy">File Content</string>
<string name="newFileButtonCopy">Create New File</string>
<string name="newFileNameHintMessage">with folder: app/test.md</string>
<string name="newFileMessageTintCopy">Commit Message</string>
<string name="newFileInvalidBranchName">Invalid branch name, may only contain &#8211;, a&#8211;z, 0&#8211;9</string>
<string name="newFileCommitMessageError">Commit message is too long</string>
<string name="newFileSuccessMessage">New file created</string>
<string name="newFileOldBranches">Current Branches</string>
<string name="newFileRequiredFields">Fields like filename, contents and commit message are required.</string>
<string name="newFileCurrentBranchMessage">Selecting current branch will disable new branch</string>
<string name="newFileNewBranchMessage">e.g: new-branch</string>
<string name="newFileRequiredFieldNewBranchName">New branch name cannot be empty if current branch is not selected</string>
<!-- generic copy -->
<string name="okButton">OK</string>
<string name="doneButton">Done</string>
<string name="doneButton">Fertig</string>
<string name="cancelButton">Abbrechen</string>
<string name="genericError">Etwas ist schief gelaufen. Bitte versuche es noch ein mal</string>
<string name="apiNotFound">Diese Anfrage erfordert Gitea 1.7 oder höher!</string>
<string name="apiNotFound">Diese Anfrage erfordert Gitea 1.7 oder höher</string>
<string name="noDataFound">Keine Daten gefunden</string>
<string name="addButton">Hinzufügen</string>
<string name="removeButton">Entfernen</string>
@ -412,9 +440,10 @@
<string name="modifiedText">Bearbeitet</string>
<string name="saveButton">Speichern</string>
<string name="nameText">Name</string>
<string name="descriptionText">Description</string>
<string name="descriptionText">Beschreibung</string>
<string name="websiteText">Website</string>
<string name="locationText">Location</string>
<string name="locationText">Standort</string>
<string name="characters255Limit">Max 255 characters</string>
<!-- generic copy -->
</resources>

View File

@ -397,6 +397,33 @@
<string name="loginOTP">OTP Code (Optional)</string>
<string name="otpMessage">Enter the otp code if 2FA is enabled</string>
<string name="repoStargazersInMenu">Stargazers</string>
<string name="repoWatchersInMenu">Watchers</string>
<string name="noDataStargazers">No stars found</string>
<string name="noDataWatchers">No watchers found</string>
<string name="starMember">Star</string>
<string name="watcherMember">Watcher</string>
<string name="commitLinkBranchesTab">Commit</string>
<string name="zipArchiveDownloadReleasesTab">Zip Archive</string>
<string name="tarArchiveDownloadReleasesTab">Tar Archive</string>
<!-- new file -->
<string name="newFileNameTintCopy">File Name</string>
<string name="newFileBranchTintCopy">Branch Name</string>
<string name="newFileContentTintCopy">File Content</string>
<string name="newFileButtonCopy">Create New File</string>
<string name="newFileNameHintMessage">with folder: app/test.md</string>
<string name="newFileMessageTintCopy">Commit Message</string>
<string name="newFileInvalidBranchName">Invalid branch name, may only contain &#8211;, a&#8211;z, 0&#8211;9</string>
<string name="newFileCommitMessageError">Commit message is too long</string>
<string name="newFileSuccessMessage">New file created</string>
<string name="newFileOldBranches">Current Branches</string>
<string name="newFileRequiredFields">Fields like filename, contents and commit message are required.</string>
<string name="newFileCurrentBranchMessage">Selecting current branch will disable new branch</string>
<string name="newFileNewBranchMessage">e.g: new-branch</string>
<string name="newFileRequiredFieldNewBranchName">New branch name cannot be empty if current branch is not selected</string>
<!-- generic copy -->
<string name="okButton">OK</string>
<string name="doneButton">Done</string>
@ -416,6 +443,8 @@
<string name="descriptionText">Description</string>
<string name="websiteText">Website</string>
<string name="locationText">Location</string>
<string name="openWebRepo">Ouvrir avec le Browser</string>
<string name="characters255Limit">Max 255 characters</string>
<!-- generic copy -->
</resources>

View File

@ -397,6 +397,33 @@
<string name="loginOTP">OTP Code (Optional)</string>
<string name="otpMessage">Enter the otp code if 2FA is enabled</string>
<string name="repoStargazersInMenu">Stargazers</string>
<string name="repoWatchersInMenu">Watchers</string>
<string name="noDataStargazers">No stars found</string>
<string name="noDataWatchers">No watchers found</string>
<string name="starMember">Star</string>
<string name="watcherMember">Watcher</string>
<string name="commitLinkBranchesTab">Commit</string>
<string name="zipArchiveDownloadReleasesTab">Zip Archive</string>
<string name="tarArchiveDownloadReleasesTab">Tar Archive</string>
<!-- new file -->
<string name="newFileNameTintCopy">File Name</string>
<string name="newFileBranchTintCopy">Branch Name</string>
<string name="newFileContentTintCopy">File Content</string>
<string name="newFileButtonCopy">Create New File</string>
<string name="newFileNameHintMessage">with folder: app/test.md</string>
<string name="newFileMessageTintCopy">Commit Message</string>
<string name="newFileInvalidBranchName">Invalid branch name, may only contain &#8211;, a&#8211;z, 0&#8211;9</string>
<string name="newFileCommitMessageError">Commit message is too long</string>
<string name="newFileSuccessMessage">New file created</string>
<string name="newFileOldBranches">Current Branches</string>
<string name="newFileRequiredFields">Fields like filename, contents and commit message are required.</string>
<string name="newFileCurrentBranchMessage">Selecting current branch will disable new branch</string>
<string name="newFileNewBranchMessage">e.g: new-branch</string>
<string name="newFileRequiredFieldNewBranchName">New branch name cannot be empty if current branch is not selected</string>
<!-- generic copy -->
<string name="okButton">OK</string>
<string name="doneButton">Готово</string>
@ -416,6 +443,8 @@
<string name="descriptionText">Описание</string>
<string name="websiteText">Веб-сайт</string>
<string name="locationText">Место расположения</string>
<string name="openWebRepo">Открыть с помощью браузера</string>
<string name="characters255Limit">Max 255 characters</string>
<!-- generic copy -->
</resources>

View File

@ -40,20 +40,21 @@
<string name="pageTitleMyRepos">My Repositories</string>
<string name="pageTitleRepositories">Repositories</string>
<string name="pageTitleProfile">Profile</string>
<string name="pageTitleNewRepo">Create Repository</string>
<string name="pageTitleNewRepo">New Repository</string>
<string name="pageTitleOrganizations">Organizations</string>
<string name="pageTitleIssues">Issues</string>
<string name="pageTitleSettings">Settings</string>
<string name="pageTitleCreateOrganization">Create Organization</string>
<string name="pageTitleCreateMilestone">Create Milestone</string>
<string name="pageTitleCreateNewIssue">Create Issue</string>
<string name="pageTitleCreateLabel">Create Label</string>
<string name="pageTitleCreateOrganization">New Organization</string>
<string name="pageTitleCreateMilestone">New Milestone</string>
<string name="pageTitleCreateNewIssue">New Issue</string>
<string name="pageTitleCreateLabel">New Label</string>
<string name="pageTitleCredits">Credits</string>
<string name="pageTitleLabelUpdate">Update Label</string>
<string name="pageTitleSponsors">Sponsors</string>
<string name="pageTitleStarredRepos">Starred Repositories</string>
<string name="pageTitleCreateTeam">Create Team</string>
<string name="pageTitleCreateTeam">New Team</string>
<string name="pageTitleAddEmail">Add Email Address</string>
<string name="pageTitleNewFile">New File</string>
<!-- page titles -->
<string name="appVersion">Version\u0020:\u0020</string>
@ -98,7 +99,6 @@
<string name="emptyFieldPassword">Password is required</string>
<string name="checkNetConnection">Cannot access network, please check your Internet connection</string>
<string name="emptyFields">All fields are required</string>
<string name="repoNameErrorEmpty">Repository name is empty</string>
<string name="repoNameErrorInvalid">Repository name is not valid. [a&#8211;z A&#8211;Z 0&#8211;9 &#8211; _]</string>
@ -260,7 +260,7 @@
<string name="noMoreData">No more data available.</string>
<string name="createLabel">Create Label</string>
<string name="createLabel">New Label</string>
<string name="menuTitleText">Repo Menu</string>
<string name="labelName">Label Name</string>
<string name="labelColor">Label Color</string>
@ -299,7 +299,7 @@
<string name="orgTabRepos">Repositories</string>
<string name="orgTabTeams">Teams</string>
<string name="orgTabMembers">Members</string>
<string name="orgCreateTeam">Create Team</string>
<string name="orgCreateTeam">New Team</string>
<string name="noDataTeams">No teams found</string>
<string name="teamTitle">Team name</string>
<string name="teamDescription">Team desc</string>
@ -387,7 +387,7 @@
<string name="repoMetaData">Repository Meta</string>
<!-- admin -->
<string name="adminCreateNewUser">Create New User</string>
<string name="adminCreateNewUser">Add New User</string>
<string name="adminUsers">Users</string>
<string name="userRoleAdmin">Admin</string>
<!-- admin -->
@ -400,13 +400,14 @@
<string name="userInvalidFullName">Invalid Full Name</string>
<string name="userInvalidUserName">Invalid Username</string>
<string name="userInvalidEmail">Invalid Email</string>
<string name="userCreatedText">New user created successfully</string>
<string name="userCreatedText">New user added successfully</string>
<string name="userExistsError">User already exists</string>
<!-- create user -->
<!-- sponsors -->
<string name="liberaPayText" translatable="false">Liberapay</string>
<string name="liberaPaySponsorsFabian" translatable="false">Fabian Stamm</string>
<string name="liberaPaySponsorsThomas" translatable="false">Thomas Schneider <a href="https://framapiaf.org/@fedilab">@Fedilab</a></string>
<!-- sponsors -->
<!-- edit issue -->
@ -415,7 +416,7 @@
<!-- edit issue -->
<!-- release -->
<string name="createRelease">Create Release</string>
<string name="createRelease">New Release</string>
<string name="releaseTagNameText">Tag Name</string>
<string name="releaseTitleText">Title</string>
<string name="releaseContentText">Content</string>
@ -432,6 +433,35 @@
<string name="loginOTP">OTP Code (Optional)</string>
<string name="otpMessage">Enter the otp code if 2FA is enabled</string>
<string name="openWebRepo">Open in Browser</string>
<string name="repoStargazersInMenu">Stargazers</string>
<string name="repoWatchersInMenu">Watchers</string>
<string name="noDataStargazers">No stars found</string>
<string name="noDataWatchers">No watchers found</string>
<string name="starMember">Star</string>
<string name="watcherMember">Watcher</string>
<string name="commitLinkBranchesTab">Commit</string>
<string name="zipArchiveDownloadReleasesTab">Zip Archive</string>
<string name="tarArchiveDownloadReleasesTab">Tar Archive</string>
<!-- new file -->
<string name="newFileNameTintCopy">File Name</string>
<string name="newFileBranchTintCopy">New Branch Name</string>
<string name="newFileContentTintCopy">File Content</string>
<string name="newFileButtonCopy">Create New File</string>
<string name="newFileNameHintMessage">with folder: app/test.md</string>
<string name="newFileMessageTintCopy">Commit Message</string>
<string name="newFileInvalidBranchName">Invalid branch name, may only contain &#8211;, a&#8211;z, 0&#8211;9</string>
<string name="newFileCommitMessageError">Commit message is too long</string>
<string name="newFileSuccessMessage">New file created</string>
<string name="newFileOldBranches">Current Branches</string>
<string name="newFileRequiredFields">Fields like filename, content and commit message are required</string>
<string name="newFileCurrentBranchMessage">Selecting current branch will disable new branch</string>
<string name="newFileNewBranchMessage">e.g: new-branch</string>
<string name="newFileRequiredFieldNewBranchName">New branch name cannot be empty if current branch is not selected</string>
<!-- generic copy -->
<string name="okButton">OK</string>
<string name="doneButton">Done</string>
@ -454,6 +484,8 @@
<string name="descriptionText">Description</string>
<string name="websiteText">Website</string>
<string name="locationText">Location</string>
<string name="characters255Limit">Max 255 characters</string>
<string name="emptyFields">All fields are required</string>
<!-- generic copy -->
</resources>

View File

@ -7,7 +7,7 @@ buildscript {
jcenter()
}
dependencies {
classpath 'com.android.tools.build:gradle:3.4.0'
classpath 'com.android.tools.build:gradle:3.5.0'
}
}

View File

@ -0,0 +1,14 @@
- New: Create new files
- New: Open repository in browser from bottomsheet, @6543
- New: List of repository stargazers
- New: List of repository watchers
- New: Open repository in browser from listview
- Enhancement: Repo website linking
- Enhancement: Reduce large text to small for links
- Enhancement: Translations for french, german
- Fixed: Crash on tapping search icon
- Fixed: Crash when tabs are moved quickly
- Fixed: Commit hash url in branches tab
For more, check the release notes.

View File

@ -2,6 +2,7 @@ GitNex is a free, open-source Android client for Git repository management tool
# Features
- Create new files
- My Repositories
- Repositories list
- Organizations list
@ -29,6 +30,6 @@ GitNex is a free, open-source Android client for Git repository management tool
- Option to access local non-https installs
- Login/Logout
More features - https://gitlab.com/mmarif4u/gitnex/wikis/Features
More features - https://gitea.com/mmarif/GitNex/wiki/Features
Developer: https://mastodon.social/@mmarif

Binary file not shown.

Before

Width:  |  Height:  |  Size: 52 KiB

After

Width:  |  Height:  |  Size: 59 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 90 KiB

After

Width:  |  Height:  |  Size: 90 KiB

Binary file not shown.

Before

Width:  |  Height:  |  Size: 33 KiB

After

Width:  |  Height:  |  Size: 71 KiB

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