gradle update, bug fix, renamed class

This commit is contained in:
nuclearfog 2022-02-27 18:47:10 +01:00
parent b4e504e4fb
commit 325f2ded19
No known key found for this signature in database
GPG Key ID: AA0271FBE406DB98
12 changed files with 169 additions and 155 deletions

View File

@ -1,9 +1,7 @@
package org.nuclearfog.twidda.adapter;
import static androidx.recyclerview.widget.RecyclerView.NO_POSITION;
import static org.nuclearfog.twidda.adapter.holder.LoginHolder.IDX_CREATED;
import static org.nuclearfog.twidda.adapter.holder.LoginHolder.IDX_SCR_NAME;
import static org.nuclearfog.twidda.adapter.holder.LoginHolder.IDX_USERNAME;
import static org.nuclearfog.twidda.adapter.holder.LoginHolder.*;
import android.content.Context;
import android.content.res.Resources;
@ -21,7 +19,6 @@ import org.nuclearfog.twidda.adapter.holder.LoginHolder;
import org.nuclearfog.twidda.backend.utils.PicassoBuilder;
import org.nuclearfog.twidda.backend.utils.StringTools;
import org.nuclearfog.twidda.database.GlobalSettings;
import org.nuclearfog.twidda.fragments.AccountFragment;
import org.nuclearfog.twidda.model.Account;
import org.nuclearfog.twidda.model.User;
@ -31,9 +28,10 @@ import java.util.List;
import jp.wasabeef.picasso.transformations.RoundedCornersTransformation;
/**
* adapter for {@link AccountFragment}
* custom {@link androidx.recyclerview.widget.RecyclerView} adapter to show a list of accounts
*
* @author nuclearfog
* @see org.nuclearfog.twidda.fragments.AccountFragment
*/
public class AccountAdapter extends Adapter<LoginHolder> {

View File

@ -1,28 +1,8 @@
package org.nuclearfog.twidda.adapter;
import static org.nuclearfog.twidda.fragments.TweetFragment.KEY_FRAG_TWEET_ID;
import static org.nuclearfog.twidda.fragments.TweetFragment.KEY_FRAG_TWEET_MODE;
import static org.nuclearfog.twidda.fragments.TweetFragment.KEY_FRAG_TWEET_SEARCH;
import static org.nuclearfog.twidda.fragments.TweetFragment.TWEET_FRAG_FAVORS;
import static org.nuclearfog.twidda.fragments.TweetFragment.TWEET_FRAG_HOME;
import static org.nuclearfog.twidda.fragments.TweetFragment.TWEET_FRAG_LIST;
import static org.nuclearfog.twidda.fragments.TweetFragment.TWEET_FRAG_MENT;
import static org.nuclearfog.twidda.fragments.TweetFragment.TWEET_FRAG_SEARCH;
import static org.nuclearfog.twidda.fragments.TweetFragment.TWEET_FRAG_TWEETS;
import static org.nuclearfog.twidda.fragments.UserFragment.KEY_FRAG_DEL_USER;
import static org.nuclearfog.twidda.fragments.UserFragment.KEY_FRAG_USER_ID;
import static org.nuclearfog.twidda.fragments.UserFragment.KEY_FRAG_USER_MODE;
import static org.nuclearfog.twidda.fragments.UserFragment.KEY_FRAG_USER_SEARCH;
import static org.nuclearfog.twidda.fragments.UserFragment.USER_FRAG_BLOCKS;
import static org.nuclearfog.twidda.fragments.UserFragment.USER_FRAG_LISTS;
import static org.nuclearfog.twidda.fragments.UserFragment.USER_FRAG_MUTES;
import static org.nuclearfog.twidda.fragments.UserFragment.USER_FRAG_SEARCH;
import static org.nuclearfog.twidda.fragments.UserFragment.USER_FRAG_SUBSCR;
import static org.nuclearfog.twidda.fragments.UserListFragment.KEY_FRAG_LIST_LIST_TYPE;
import static org.nuclearfog.twidda.fragments.UserListFragment.KEY_FRAG_LIST_OWNER_ID;
import static org.nuclearfog.twidda.fragments.UserListFragment.KEY_FRAG_LIST_OWNER_NAME;
import static org.nuclearfog.twidda.fragments.UserListFragment.LIST_USER_OWNS;
import static org.nuclearfog.twidda.fragments.UserListFragment.LIST_USER_SUBSCR_TO;
import static org.nuclearfog.twidda.fragments.TweetFragment.*;
import static org.nuclearfog.twidda.fragments.UserFragment.*;
import static org.nuclearfog.twidda.fragments.UserListFragment.*;
import android.os.Bundle;
@ -38,7 +18,7 @@ import org.nuclearfog.twidda.fragments.UserFragment;
import org.nuclearfog.twidda.fragments.UserListFragment;
/**
* Fragment adapter for ViewPager
* custom adapter used for {@link androidx.viewpager.widget.ViewPager}
*
* @author nuclearfog
*/

View File

@ -23,9 +23,10 @@ import java.util.Arrays;
import java.util.List;
/**
* Adapter class for image previews
* custom {@link androidx.recyclerview.widget.RecyclerView} adapter implementation to show image previews
*
* @author nuclearfog
* @see org.nuclearfog.twidda.activities.ImageViewer
*/
public class ImageAdapter extends Adapter<ViewHolder> {

View File

@ -32,7 +32,7 @@ import org.nuclearfog.twidda.model.User;
import jp.wasabeef.picasso.transformations.RoundedCornersTransformation;
/**
* Adapter class for direct messages list
* custom {@link androidx.recyclerview.widget.RecyclerView} adapter implementation to show directmessages
*
* @author nuclearfog
* @see org.nuclearfog.twidda.fragments.MessageFragment
@ -54,7 +54,7 @@ public class MessageAdapter extends Adapter<ViewHolder> {
*/
private static final int TYPE_FOOTER = 1;
private OnItemSelected itemClickListener;
private OnMessageClickListener itemClickListener;
private GlobalSettings settings;
private Resources resources;
private Picasso picasso;
@ -65,7 +65,7 @@ public class MessageAdapter extends Adapter<ViewHolder> {
/**
* @param itemClickListener click listener
*/
public MessageAdapter(Context context, OnItemSelected itemClickListener) {
public MessageAdapter(Context context, OnMessageClickListener itemClickListener) {
this.itemClickListener = itemClickListener;
settings = GlobalSettings.getInstance(context);
picasso = PicassoBuilder.get(context);
@ -146,44 +146,56 @@ public class MessageAdapter extends Adapter<ViewHolder> {
@Override
public ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
if (viewType == TYPE_MESSAGE) {
final MessageHolder vh = new MessageHolder(parent, settings);
vh.buttons[0].setOnClickListener(new View.OnClickListener() {
final MessageHolder holder = new MessageHolder(parent, settings);
holder.buttons[0].setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
int position = vh.getLayoutPosition();
int position = holder.getLayoutPosition();
if (position != NO_POSITION) {
itemClickListener.onClick(data.get(position), OnItemSelected.Action.ANSWER);
DirectMessage message = data.get(position);
if (message != null) {
itemClickListener.onClick(message, OnMessageClickListener.Action.ANSWER);
}
}
}
});
vh.buttons[1].setOnClickListener(new View.OnClickListener() {
holder.buttons[1].setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
int position = vh.getLayoutPosition();
int position = holder.getLayoutPosition();
if (position != NO_POSITION) {
itemClickListener.onClick(data.get(position), OnItemSelected.Action.DELETE);
DirectMessage message = data.get(position);
if (message != null) {
itemClickListener.onClick(message, OnMessageClickListener.Action.DELETE);
}
}
}
});
vh.profile_img.setOnClickListener(new View.OnClickListener() {
holder.profile_img.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
int position = vh.getLayoutPosition();
int position = holder.getLayoutPosition();
if (position != NO_POSITION) {
itemClickListener.onClick(data.get(position), OnItemSelected.Action.PROFILE);
DirectMessage message = data.get(position);
if (message != null) {
itemClickListener.onClick(message, OnMessageClickListener.Action.PROFILE);
}
}
}
});
vh.mediaButton.setOnClickListener(new View.OnClickListener() {
holder.mediaButton.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View v) {
int position = vh.getLayoutPosition();
int position = holder.getLayoutPosition();
if (position != NO_POSITION) {
itemClickListener.onClick(data.get(position), OnItemSelected.Action.MEDIA);
DirectMessage message = data.get(position);
if (message != null) {
itemClickListener.onClick(message, OnMessageClickListener.Action.MEDIA);
}
}
}
});
return vh;
return holder;
} else {
final Footer footer = new Footer(parent, settings, false);
footer.loadBtn.setOnClickListener(new View.OnClickListener() {
@ -261,9 +273,9 @@ public class MessageAdapter extends Adapter<ViewHolder> {
}
/**
* callback for the click listener
* listener for directmessage items
*/
public interface OnItemSelected extends OnTagClickListener {
public interface OnMessageClickListener extends OnTagClickListener {
/**
* Actions performed by clicking the buttons

View File

@ -24,7 +24,7 @@ import java.util.ArrayList;
import java.util.List;
/**
* Adapter class for Trend list
* custom {@link androidx.recyclerview.widget.RecyclerView} adapter implementation to show twitter trends
*
* @author nuclearfog
* @see org.nuclearfog.twidda.fragments.TrendFragment

View File

@ -38,7 +38,7 @@ import java.util.List;
import jp.wasabeef.picasso.transformations.RoundedCornersTransformation;
/**
* Adapter class for tweet list
* custom {@link androidx.recyclerview.widget.RecyclerView} adapter to show tweets
*
* @author nuclearfog
* @see org.nuclearfog.twidda.fragments.TweetFragment
@ -219,9 +219,11 @@ public class TweetAdapter extends Adapter<ViewHolder> {
@Override
public void onClick(View v) {
int position = vh.getLayoutPosition();
Tweet tweet = tweets.get(position);
if (position != NO_POSITION && tweet != null) {
itemClickListener.onTweetClick(tweet);
if (position != NO_POSITION) {
Tweet tweet = tweets.get(position);
if (tweet != null) {
itemClickListener.onTweetClick(tweet);
}
}
}
});
@ -236,12 +238,24 @@ public class TweetAdapter extends Adapter<ViewHolder> {
long sinceId = 0;
long maxId = 0;
if (position == 0) {
sinceId = tweets.get(position + 1).getId();
Tweet tweet = tweets.get(position + 1);
if (tweet != null) {
sinceId = tweet.getId();
}
} else if (position == tweets.size() - 1) {
maxId = tweets.get(position - 1).getId() - 1;
Tweet tweet = tweets.get(position - 1);
if (tweet != null) {
maxId = tweet.getId() - 1;
}
} else {
sinceId = tweets.get(position + 1).getId();
maxId = tweets.get(position - 1).getId() - 1;
Tweet tweet = tweets.get(position + 1);
if (tweet != null) {
sinceId = tweet.getId();
}
tweet = tweets.get(position - 1);
if (tweet != null) {
maxId = tweet.getId() - 1;
}
}
boolean success = itemClickListener.onPlaceholderClick(sinceId, maxId, position);
if (success) {
@ -258,56 +272,58 @@ public class TweetAdapter extends Adapter<ViewHolder> {
@Override
public void onBindViewHolder(@NonNull ViewHolder holder, int index) {
Tweet tweet = tweets.get(index);
if (holder instanceof TweetHolder && tweet != null) {
TweetHolder tweetItem = (TweetHolder) holder;
User user = tweet.getAuthor();
if (tweet.getEmbeddedTweet() != null) {
tweetItem.textViews[5].setText(user.getScreenname());
tweetItem.textViews[5].setVisibility(VISIBLE);
tweetItem.rtUser.setVisibility(VISIBLE);
tweet = tweet.getEmbeddedTweet();
user = tweet.getAuthor();
} else {
tweetItem.textViews[5].setVisibility(INVISIBLE);
tweetItem.rtUser.setVisibility(INVISIBLE);
}
Spanned text = Tagger.makeTextWithLinks(tweet.getText(), settings.getHighlightColor());
tweetItem.textViews[2].setText(text);
tweetItem.textViews[0].setText(user.getUsername());
tweetItem.textViews[1].setText(user.getScreenname());
tweetItem.textViews[3].setText(NUM_FORMAT.format(tweet.getRetweetCount()));
tweetItem.textViews[4].setText(NUM_FORMAT.format(tweet.getFavoriteCount()));
tweetItem.textViews[6].setText(formatCreationTime(resources, tweet.getTimestamp()));
if (holder instanceof TweetHolder) {
Tweet tweet = tweets.get(index);
if (tweet != null) {
TweetHolder tweetItem = (TweetHolder) holder;
User user = tweet.getAuthor();
if (tweet.getEmbeddedTweet() != null) {
tweetItem.textViews[5].setText(user.getScreenname());
tweetItem.textViews[5].setVisibility(VISIBLE);
tweetItem.rtUser.setVisibility(VISIBLE);
tweet = tweet.getEmbeddedTweet();
user = tweet.getAuthor();
} else {
tweetItem.textViews[5].setVisibility(INVISIBLE);
tweetItem.rtUser.setVisibility(INVISIBLE);
}
Spanned text = Tagger.makeTextWithLinks(tweet.getText(), settings.getHighlightColor());
tweetItem.textViews[2].setText(text);
tweetItem.textViews[0].setText(user.getUsername());
tweetItem.textViews[1].setText(user.getScreenname());
tweetItem.textViews[3].setText(NUM_FORMAT.format(tweet.getRetweetCount()));
tweetItem.textViews[4].setText(NUM_FORMAT.format(tweet.getFavoriteCount()));
tweetItem.textViews[6].setText(formatCreationTime(resources, tweet.getTimestamp()));
if (tweet.isRetweeted()) {
tweetItem.rtIcon.setColorFilter(settings.getRetweetIconColor(), SRC_IN);
} else {
tweetItem.rtIcon.setColorFilter(settings.getIconColor(), SRC_IN);
}
if (tweet.isFavorited()) {
tweetItem.favIcon.setColorFilter(settings.getFavoriteIconColor(), SRC_IN);
} else {
tweetItem.favIcon.setColorFilter(settings.getIconColor(), SRC_IN);
}
if (user.isVerified()) {
tweetItem.verifiedIcon.setVisibility(VISIBLE);
} else {
tweetItem.verifiedIcon.setVisibility(GONE);
}
if (user.isProtected()) {
tweetItem.lockedIcon.setVisibility(VISIBLE);
} else {
tweetItem.lockedIcon.setVisibility(GONE);
}
if (settings.imagesEnabled() && !user.getImageUrl().isEmpty()) {
String profileImageUrl = user.getImageUrl();
if (!user.hasDefaultProfileImage())
profileImageUrl += settings.getImageSuffix();
picasso.load(profileImageUrl).transform(new RoundedCornersTransformation(2, 0))
.error(R.drawable.no_image).into(tweetItem.profile);
} else {
tweetItem.profile.setImageResource(0);
if (tweet.isRetweeted()) {
tweetItem.rtIcon.setColorFilter(settings.getRetweetIconColor(), SRC_IN);
} else {
tweetItem.rtIcon.setColorFilter(settings.getIconColor(), SRC_IN);
}
if (tweet.isFavorited()) {
tweetItem.favIcon.setColorFilter(settings.getFavoriteIconColor(), SRC_IN);
} else {
tweetItem.favIcon.setColorFilter(settings.getIconColor(), SRC_IN);
}
if (user.isVerified()) {
tweetItem.verifiedIcon.setVisibility(VISIBLE);
} else {
tweetItem.verifiedIcon.setVisibility(GONE);
}
if (user.isProtected()) {
tweetItem.lockedIcon.setVisibility(VISIBLE);
} else {
tweetItem.lockedIcon.setVisibility(GONE);
}
if (settings.imagesEnabled() && !user.getImageUrl().isEmpty()) {
String profileImageUrl = user.getImageUrl();
if (!user.hasDefaultProfileImage())
profileImageUrl += settings.getImageSuffix();
picasso.load(profileImageUrl).transform(new RoundedCornersTransformation(2, 0))
.error(R.drawable.no_image).into(tweetItem.profile);
} else {
tweetItem.profile.setImageResource(0);
}
}
} else if (holder instanceof Footer) {
Footer footer = (Footer) holder;

View File

@ -30,7 +30,7 @@ import java.text.NumberFormat;
import jp.wasabeef.picasso.transformations.RoundedCornersTransformation;
/**
* Adapter class for user list
* custom {@link androidx.recyclerview.widget.RecyclerView} adapter implementation to show users
*
* @author nuclearfog
* @see org.nuclearfog.twidda.fragments.UserFragment
@ -168,9 +168,11 @@ public class UserAdapter extends Adapter<ViewHolder> {
@Override
public void onClick(View v) {
int position = vh.getLayoutPosition();
User user = data.get(position);
if (position != NO_POSITION && user != null) {
listener.onUserClick(user);
if (position != NO_POSITION) {
User user = data.get(position);
if (user != null) {
listener.onUserClick(user);
}
}
}
});
@ -180,9 +182,11 @@ public class UserAdapter extends Adapter<ViewHolder> {
@Override
public void onClick(View v) {
int position = vh.getLayoutPosition();
User user = data.get(position);
if (position != NO_POSITION && user != null) {
listener.onDelete(user.getScreenname());
if (position != NO_POSITION) {
User user = data.get(position);
if (user != null) {
listener.onDelete(user.getScreenname());
}
}
}
});
@ -212,31 +216,33 @@ public class UserAdapter extends Adapter<ViewHolder> {
@Override
public void onBindViewHolder(@NonNull ViewHolder holder, int index) {
User user = data.get(index);
if (holder instanceof UserHolder && user != null) {
UserHolder userholder = (UserHolder) holder;
userholder.textViews[0].setText(user.getUsername());
userholder.textViews[1].setText(user.getScreenname());
userholder.textViews[2].setText(NUM_FORMAT.format(user.getFollowing()));
userholder.textViews[3].setText(NUM_FORMAT.format(user.getFollower()));
if (user.isVerified()) {
userholder.verifyIcon.setVisibility(VISIBLE);
} else {
userholder.verifyIcon.setVisibility(GONE);
}
if (user.isProtected()) {
userholder.lockedIcon.setVisibility(VISIBLE);
} else {
userholder.lockedIcon.setVisibility(GONE);
}
if (settings.imagesEnabled() && !user.getImageUrl().isEmpty()) {
String profileImageUrl = user.getImageUrl();
if (!user.hasDefaultProfileImage())
profileImageUrl += settings.getImageSuffix();
picasso.load(profileImageUrl).transform(new RoundedCornersTransformation(2, 0))
.error(R.drawable.no_image).into(userholder.profileImg);
} else {
userholder.profileImg.setImageResource(0);
if (holder instanceof UserHolder) {
User user = data.get(index);
if (user != null) {
UserHolder userholder = (UserHolder) holder;
userholder.textViews[0].setText(user.getUsername());
userholder.textViews[1].setText(user.getScreenname());
userholder.textViews[2].setText(NUM_FORMAT.format(user.getFollowing()));
userholder.textViews[3].setText(NUM_FORMAT.format(user.getFollower()));
if (user.isVerified()) {
userholder.verifyIcon.setVisibility(VISIBLE);
} else {
userholder.verifyIcon.setVisibility(GONE);
}
if (user.isProtected()) {
userholder.lockedIcon.setVisibility(VISIBLE);
} else {
userholder.lockedIcon.setVisibility(GONE);
}
if (settings.imagesEnabled() && !user.getImageUrl().isEmpty()) {
String profileImageUrl = user.getImageUrl();
if (!user.hasDefaultProfileImage())
profileImageUrl += settings.getImageSuffix();
picasso.load(profileImageUrl).transform(new RoundedCornersTransformation(2, 0))
.error(R.drawable.no_image).into(userholder.profileImg);
} else {
userholder.profileImg.setImageResource(0);
}
}
} else if (holder instanceof Footer) {
Footer footer = (Footer) holder;

View File

@ -24,7 +24,6 @@ import org.nuclearfog.twidda.adapter.holder.ListHolder;
import org.nuclearfog.twidda.backend.lists.UserLists;
import org.nuclearfog.twidda.backend.utils.PicassoBuilder;
import org.nuclearfog.twidda.database.GlobalSettings;
import org.nuclearfog.twidda.fragments.UserListFragment;
import org.nuclearfog.twidda.model.User;
import org.nuclearfog.twidda.model.UserList;
@ -33,12 +32,12 @@ import java.text.NumberFormat;
import jp.wasabeef.picasso.transformations.RoundedCornersTransformation;
/**
* Adapter class for user lists
* custom {@link androidx.recyclerview.widget.RecyclerView} adapter implementation to show userlists
*
* @author nuclearfog
* @see UserListFragment
* @see org.nuclearfog.twidda.fragments.UserListFragment
*/
public class ListAdapter extends Adapter<ViewHolder> {
public class UserlistAdapter extends Adapter<ViewHolder> {
/**
* indicator if there is no footer
@ -71,7 +70,7 @@ public class ListAdapter extends Adapter<ViewHolder> {
/**
* @param listener item click listener
*/
public ListAdapter(Context context, ListClickListener listener) {
public UserlistAdapter(Context context, ListClickListener listener) {
this.listener = listener;
settings = GlobalSettings.getInstance(context);
picasso = PicassoBuilder.get(context);
@ -177,8 +176,10 @@ public class ListAdapter extends Adapter<ViewHolder> {
public void onClick(View v) {
int position = itemHolder.getLayoutPosition();
if (position != NO_POSITION) {
UserList list = data.get(position);
listener.onListClick(list);
UserList item = data.get(position);
if (item != null) {
listener.onListClick(item);
}
}
}
});

View File

@ -79,7 +79,7 @@ public abstract class ListFragment extends Fragment implements OnRefreshListener
* @return true if swipe view is active
*/
protected boolean isRefreshing() {
return isRefreshing;
return isRefreshing || reload.isRefreshing();
}
/**

View File

@ -26,7 +26,7 @@ import org.nuclearfog.twidda.activities.SearchPage;
import org.nuclearfog.twidda.activities.TweetActivity;
import org.nuclearfog.twidda.activities.UserProfile;
import org.nuclearfog.twidda.adapter.MessageAdapter;
import org.nuclearfog.twidda.adapter.MessageAdapter.OnItemSelected;
import org.nuclearfog.twidda.adapter.MessageAdapter.OnMessageClickListener;
import org.nuclearfog.twidda.backend.MessageLoader;
import org.nuclearfog.twidda.backend.lists.Directmessages;
import org.nuclearfog.twidda.backend.utils.ErrorHandler;
@ -40,7 +40,7 @@ import org.nuclearfog.twidda.model.DirectMessage;
*
* @author nuclearfog
*/
public class MessageFragment extends ListFragment implements OnItemSelected, OnConfirmListener {
public class MessageFragment extends ListFragment implements OnMessageClickListener, OnConfirmListener {
private MessageLoader messageTask;
private MessageAdapter adapter;

View File

@ -14,8 +14,8 @@ import androidx.annotation.Nullable;
import org.nuclearfog.twidda.activities.UserProfile;
import org.nuclearfog.twidda.activities.UserlistActivity;
import org.nuclearfog.twidda.adapter.ListAdapter;
import org.nuclearfog.twidda.adapter.ListAdapter.ListClickListener;
import org.nuclearfog.twidda.adapter.UserlistAdapter;
import org.nuclearfog.twidda.adapter.UserlistAdapter.ListClickListener;
import org.nuclearfog.twidda.backend.ListLoader;
import org.nuclearfog.twidda.backend.lists.UserLists;
import org.nuclearfog.twidda.backend.utils.ErrorHandler;
@ -61,7 +61,7 @@ public class UserListFragment extends ListFragment implements ListClickListener
public static final int REQUEST_OPEN_LIST = 0x9541;
private ListLoader listTask;
private ListAdapter adapter;
private UserlistAdapter adapter;
private String ownerName = "";
private long id = 0;
@ -77,7 +77,7 @@ public class UserListFragment extends ListFragment implements ListClickListener
ownerName = param.getString(KEY_FRAG_LIST_OWNER_NAME, "");
type = param.getInt(KEY_FRAG_LIST_LIST_TYPE);
}
adapter = new ListAdapter(requireContext(), this);
adapter = new UserlistAdapter(requireContext(), this);
setAdapter(adapter);
}

View File

@ -9,8 +9,8 @@ buildscript {
}
dependencies {
classpath 'com.android.tools.build:gradle:7.1.1'
classpath 'io.michaelrocks:paranoid-gradle-plugin:0.3.5'
classpath 'com.android.tools.build:gradle:7.1.2'
classpath 'io.michaelrocks:paranoid-gradle-plugin:0.3.7'
classpath 'gradle.plugin.ru.cleverpumpkin.proguard-dictionaries-generator:plugin:1.0.8'
}
}