Skip to content

Commit 67e0ade

Browse files
committed
added:
- text transcends into the other
1 parent 7a3a7a2 commit 67e0ade

File tree

6 files changed

+201
-16
lines changed

6 files changed

+201
-16
lines changed

.idea/gradle.xml

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

.idea/misc.xml

Lines changed: 1 addition & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

app/button/src/main/java/cls/android/button/Button.java

Lines changed: 76 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,7 @@
1212
import androidx.annotation.NonNull;
1313
import androidx.annotation.Nullable;
1414
import androidx.constraintlayout.motion.widget.MotionLayout;
15+
import androidx.constraintlayout.widget.ConstraintLayout;
1516

1617
public class Button extends FrameLayout {
1718
public static final int START = 0;
@@ -23,11 +24,15 @@ public class Button extends FrameLayout {
2324
private TextView textOneView;
2425
private TextView textTwoView;
2526
private ImageView imageView;
27+
private ConstraintLayout btnInsideParent;
28+
private View background;
2629

2730
private String textOne = "Placeholder I";
2831
private String textTwo = "Placeholder II";
2932
private Drawable img;
3033
private boolean isVibrationEnabled = false;
34+
private MotionLayout.TransitionListener transitionListener;
35+
private ButtonTextAnimator buttonTextAnimator;
3136

3237

3338
public Button(@NonNull Context context) {
@@ -54,6 +59,12 @@ private void init() {
5459
LayoutInflater.from(getContext()).inflate(R.layout.layout_button_swipe,this);
5560
initViews();
5661
setupViews();
62+
setupAnimator();
63+
64+
}
65+
66+
private void setupAnimator() {
67+
buttonTextAnimator = new ButtonTextAnimator(this);
5768
}
5869

5970
private void setupViews() {
@@ -65,43 +76,59 @@ private void setupViews() {
6576
}
6677

6778
private void initListener() {
68-
motionLayout.setTransitionListener(new MotionLayout.TransitionListener() {
79+
transitionListener = new MotionLayout.TransitionListener() {
80+
private int i1;
81+
private int i;
82+
6983
@Override
7084
public void onTransitionStarted(MotionLayout motionLayout, int i, int i1) {
7185

7286
}
7387

7488
@Override
7589
public void onTransitionChange(MotionLayout motionLayout, int i, int i1, float v) {
90+
this.i = i;
91+
this.i1 = i1;
92+
buttonTextAnimator.notifyTransitionChange(motionLayout,i,i1,v);
93+
94+
7695

7796
}
7897

7998
@Override
8099
public void onTransitionCompleted(MotionLayout motionLayout, int i) {
81100
if (isVibrationEnabled)
82101
HardwareUtil.vibrate(getContext());
83-
if (onSwipeListener != null)
84-
onSwipeListener
85-
.onChange(
86-
motionLayout.getCurrentState() == motionLayout.getStartState() ?
87-
START : END
88-
);
102+
notifyStateChange(motionLayout);
103+
89104

90105
}
91106

92107
@Override
93108
public void onTransitionTrigger(MotionLayout motionLayout, int i, boolean b, float v) {
94109

95110
}
96-
});
111+
};
112+
motionLayout.setTransitionListener(transitionListener);
97113

98114
}
99115

116+
private void notifyStateChange(MotionLayout motionLayout) {
117+
if (onSwipeListener != null)
118+
onSwipeListener
119+
.onChange(
120+
motionLayout.getCurrentState() == motionLayout.getStartState() ?
121+
START : END
122+
);
123+
}
124+
100125
private void initViews() {
101126
motionLayout = findViewById(R.id.motionlayout);
102127
textOneView = findViewById(R.id.text);
103128
textTwoView = findViewById(R.id.text2);
104129
imageView = findViewById(R.id.image);
130+
btnInsideParent = findViewById(R.id.constraint_swipe_inner_btn);
131+
background = findViewById(R.id.view);
105132
}
106133

107134
public void setOnSwipeListener(OnStateChangedListener onSwipeListener){
@@ -151,4 +178,45 @@ public void setImg(Drawable img) {
151178
postInvalidate();
152179

153180
}
181+
182+
public MotionLayout.TransitionListener getTransitionListener() {
183+
return transitionListener;
184+
}
185+
186+
public void setTransitionListener(MotionLayout.TransitionListener transitionListener) {
187+
this.transitionListener = transitionListener;
188+
motionLayout.setTransitionListener(transitionListener);
189+
}
190+
191+
public TextView getTextOneView() {
192+
return textOneView;
193+
}
194+
195+
public void setTextOneView(TextView textOneView) {
196+
this.textOneView = textOneView;
197+
}
198+
199+
public TextView getTextTwoView() {
200+
return textTwoView;
201+
}
202+
203+
public void setTextTwoView(TextView textTwoView) {
204+
this.textTwoView = textTwoView;
205+
}
206+
207+
public ConstraintLayout getBtnInsideParent() {
208+
return btnInsideParent;
209+
}
210+
211+
public void setBtnInsideParent(ConstraintLayout btnInsideParent) {
212+
this.btnInsideParent = btnInsideParent;
213+
}
214+
215+
public View getBackgroundView() {
216+
return background;
217+
}
218+
219+
public void setBackground(View background) {
220+
this.background = background;
221+
}
154222
}
Lines changed: 107 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,107 @@
1+
package cls.android.button;
2+
3+
import android.graphics.Color;
4+
import android.text.Spannable;
5+
import android.text.SpannableString;
6+
import android.text.style.ForegroundColorSpan;
7+
import android.util.Log;
8+
import android.widget.TextView;
9+
10+
import androidx.constraintlayout.motion.widget.MotionLayout;
11+
import androidx.core.content.ContextCompat;
12+
13+
public class ButtonTextAnimator {
14+
private final Button button;
15+
16+
public ButtonTextAnimator(Button button) {
17+
this.button = button;
18+
}
19+
20+
public void notifyTransitionChange(MotionLayout motionLayout, int startId, int endId, float percentageOfAnimDone) {
21+
TextView start = null;
22+
TextView end = null;
23+
Log.d(TAG, "notifyTransitionChange: " + percentageOfAnimDone);
24+
if (startId == R.id.end){
25+
start = button.getTextTwoView();
26+
end = button.getTextOneView();
27+
28+
}
29+
else if(startId == R.id.start){
30+
start = button.getTextOneView();
31+
end = button.getTextTwoView();
32+
}
33+
taskTextAnim(motionLayout,percentageOfAnimDone,startId,endId,start,1);
34+
taskTextAnim(motionLayout,percentageOfAnimDone,startId,endId,end,-1);
35+
36+
37+
38+
39+
40+
41+
42+
}
43+
44+
private void taskAddTextTwo(MotionLayout motionLayout, float percentageOfAnimDone, int i1, int v, TextView add) {
45+
46+
47+
}
48+
49+
private void taskTextAnim(MotionLayout motionLayout, float percentageOfAnimDone, int i1, int v, TextView remove, int i) {
50+
Log.d(TAG, "taskRemoveTextOne:123 " + percentageOfAnimDone);
51+
float textWidthOne = button.getTextOneView().getPaint().measureText(button.getTextOne());
52+
float charWidth =
53+
remove.getPaint().measureText(remove.getText().toString()) / remove.getText().length();
54+
55+
float parentAnimWidth = button.getBackgroundView().getWidth() -
56+
(2* button.getResources().getDimensionPixelSize(R.dimen.margin_regular));
57+
58+
double percentageTextOneInsideOfParent = 100/parentAnimWidth * textWidthOne;
59+
String s = remove.getText().toString();
60+
61+
double startOfTextOneFromStart = parentAnimWidth * ((1-percentageTextOneInsideOfParent /100)/2);
62+
double animBtnPositionX = percentageOfAnimDone * parentAnimWidth;
63+
double diff = animBtnPositionX - startOfTextOneFromStart;
64+
Spannable spannable = new SpannableString(s);
65+
Log.d(TAG, "taskRemoveTextOne: " + percentageOfAnimDone);
66+
if (diff > 0){
67+
Log.d(TAG, "taskRemoveTextOne:1232 " + diff +" " + percentageOfAnimDone);
68+
int pos = Math.toIntExact(Math.round(diff / charWidth));
69+
if (pos > s.length()) {
70+
if(i == 1) {
71+
spannable.setSpan(new ForegroundColorSpan(Color.parseColor("#00000000")), 0, s.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
72+
}
73+
else{
74+
spannable.setSpan(new ForegroundColorSpan(ContextCompat.getColor(button.getContext(), R.color.black_original)), 0, s.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
75+
76+
}
77+
remove.setText(spannable);
78+
return;
79+
}
80+
if (i == 1) {
81+
spannable.setSpan(new ForegroundColorSpan(Color.parseColor("#00000000")), 0, pos, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
82+
spannable.setSpan(new ForegroundColorSpan(ContextCompat.getColor(button.getContext(), R.color.white_original)), pos, s.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
83+
}
84+
else{
85+
spannable.setSpan(new ForegroundColorSpan(ContextCompat.getColor(button.getContext(),R.color.black_original)), 0, pos, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
86+
spannable.setSpan(new ForegroundColorSpan(Color.parseColor("#00000000")), pos, s.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
87+
}
88+
remove.setText(spannable);
89+
90+
}
91+
else{
92+
if (i == 1) {
93+
spannable.setSpan(new ForegroundColorSpan(ContextCompat.getColor(button.getContext(), R.color.white_original)), 0, s.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
94+
}
95+
else{
96+
spannable.setSpan(new ForegroundColorSpan(Color.parseColor("#00000000")), 0, s.length(), Spannable.SPAN_EXCLUSIVE_EXCLUSIVE);
97+
}
98+
remove.setText(spannable);
99+
100+
}
101+
102+
103+
104+
}
105+
106+
private static final String TAG = "ButtonTextAnimator";
107+
}

app/button/src/main/res/layout/layout_button_swipe.xml

Lines changed: 9 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -50,20 +50,24 @@
5050
android:layout_height="wrap_content"
5151
app:layout_constraintStart_toStartOf="parent"
5252
app:layout_constraintEnd_toEndOf="parent"
53+
android:textAlignment="textEnd"
5354
app:layout_constraintBottom_toBottomOf="parent"
5455
app:layout_constraintTop_toTopOf="parent"
5556
android:textColor="@color/white_original"
5657
android:text="Slide To Remove" />
58+
5759
<TextView
5860
android:id="@+id/text2"
5961
android:layout_width="wrap_content"
6062
android:layout_height="wrap_content"
61-
app:layout_constraintStart_toStartOf="parent"
62-
app:layout_constraintEnd_toEndOf="parent"
63+
android:text="Tap to Undo"
64+
android:textAlignment="textStart"
65+
66+
android:textColor="#00000000"
6367
app:layout_constraintBottom_toBottomOf="parent"
64-
app:layout_constraintTop_toTopOf="parent"
65-
android:textColor="@color/black_original"
66-
android:text="Tap to Undo" />
68+
app:layout_constraintEnd_toEndOf="parent"
69+
app:layout_constraintStart_toStartOf="parent"
70+
app:layout_constraintTop_toTopOf="parent" />
6771

6872
<androidx.constraintlayout.widget.ConstraintLayout
6973
android:id="@+id/constraint_swipe_inner_btn"

app/button/src/main/res/xml/layout_button_swipe_scene.xml

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -37,7 +37,7 @@
3737
<Constraint android:id="@+id/text2">
3838
<CustomAttribute
3939
motion:attributeName="alpha"
40-
motion:customFloatValue="0.0"
40+
motion:customFloatValue="1.0"
4141
/>
4242
</Constraint>
4343
</ConstraintSet>
@@ -69,7 +69,7 @@
6969
<Constraint android:id="@+id/text">
7070
<CustomAttribute
7171
motion:attributeName="alpha"
72-
motion:customFloatValue="0.0"
72+
motion:customFloatValue="1.0"
7373
/>
7474
</Constraint>
7575
<Constraint android:id="@+id/text2">
@@ -89,5 +89,10 @@
8989
motion:touchAnchorId="@+id/constraint_swipe_inner_btn"
9090
motion:touchAnchorSide="right"
9191
motion:dragDirection="dragRight" />
92+
93+
94+
9295
</Transition>
96+
97+
9398
</MotionScene>

0 commit comments

Comments
 (0)