react-native-highlight-text-view 0.1.23 → 0.1.24
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
|
@@ -33,7 +33,9 @@ class RoundedBackgroundSpan(
|
|
|
33
33
|
internal val backgroundInsetRight: Float,
|
|
34
34
|
internal val cornerRadius: Float,
|
|
35
35
|
internal val isLineStart: Boolean = false,
|
|
36
|
-
internal val isLineEnd: Boolean = false
|
|
36
|
+
internal val isLineEnd: Boolean = false,
|
|
37
|
+
internal val isFirstLine: Boolean = false,
|
|
38
|
+
internal val isLastLine: Boolean = false
|
|
37
39
|
) : ReplacementSpan() {
|
|
38
40
|
|
|
39
41
|
override fun getSize(
|
|
@@ -123,37 +125,37 @@ class RoundedBackgroundSpan(
|
|
|
123
125
|
canvas.drawRoundRect(rect, cornerRadius, cornerRadius, bgPaint)
|
|
124
126
|
}
|
|
125
127
|
isLineStart -> {
|
|
126
|
-
// Line START - round LEFT corners
|
|
128
|
+
// Line START - round LEFT corners (top and bottom)
|
|
127
129
|
val path = android.graphics.Path()
|
|
128
130
|
path.addRoundRect(
|
|
129
131
|
rect,
|
|
130
132
|
floatArrayOf(
|
|
131
|
-
cornerRadius, cornerRadius,
|
|
132
|
-
0f, 0f,
|
|
133
|
-
0f, 0f,
|
|
134
|
-
cornerRadius, cornerRadius
|
|
133
|
+
cornerRadius, cornerRadius, // top-left
|
|
134
|
+
0f, 0f, // top-right
|
|
135
|
+
0f, 0f, // bottom-right
|
|
136
|
+
cornerRadius, cornerRadius // bottom-left
|
|
135
137
|
),
|
|
136
138
|
android.graphics.Path.Direction.CW
|
|
137
139
|
)
|
|
138
140
|
canvas.drawPath(path, bgPaint)
|
|
139
141
|
}
|
|
140
142
|
isLineEnd -> {
|
|
141
|
-
// Line END - round RIGHT corners
|
|
143
|
+
// Line END - round RIGHT corners (top and bottom)
|
|
142
144
|
val path = android.graphics.Path()
|
|
143
145
|
path.addRoundRect(
|
|
144
146
|
rect,
|
|
145
147
|
floatArrayOf(
|
|
146
|
-
0f, 0f,
|
|
147
|
-
cornerRadius, cornerRadius,
|
|
148
|
-
cornerRadius, cornerRadius,
|
|
149
|
-
0f, 0f
|
|
148
|
+
0f, 0f, // top-left
|
|
149
|
+
cornerRadius, cornerRadius, // top-right
|
|
150
|
+
cornerRadius, cornerRadius, // bottom-right
|
|
151
|
+
0f, 0f // bottom-left
|
|
150
152
|
),
|
|
151
153
|
android.graphics.Path.Direction.CW
|
|
152
154
|
)
|
|
153
155
|
canvas.drawPath(path, bgPaint)
|
|
154
156
|
}
|
|
155
157
|
else -> {
|
|
156
|
-
// Middle - NO rounded corners (
|
|
158
|
+
// Middle characters - NO rounded corners (square) for smooth edges
|
|
157
159
|
canvas.drawRect(rect, bgPaint)
|
|
158
160
|
}
|
|
159
161
|
}
|
|
@@ -486,12 +488,19 @@ class HighlightTextView : AppCompatEditText {
|
|
|
486
488
|
var isAtLineStart = i == 0 || hasNewlineBefore
|
|
487
489
|
var isAtLineEnd = i == textStr.length - 1 || hasNewlineAfter
|
|
488
490
|
|
|
491
|
+
// Determine if this is the first or last line
|
|
492
|
+
var isOnFirstLine = i == 0 || hasNewlineBefore
|
|
493
|
+
var isOnLastLine = i == textStr.length - 1 || hasNewlineAfter
|
|
494
|
+
|
|
489
495
|
// Only use layout for auto-wrapped lines (not manual newlines)
|
|
490
496
|
if (!hasNewlineBefore && !hasNewlineAfter && layout != null && i < textStr.length) {
|
|
491
497
|
try {
|
|
492
498
|
val line = layout.getLineForOffset(i)
|
|
493
499
|
val lineStart = layout.getLineStart(line)
|
|
494
500
|
val lineEnd = layout.getLineEnd(line)
|
|
501
|
+
// Check if this is the first or last line
|
|
502
|
+
isOnFirstLine = line == 0
|
|
503
|
+
isOnLastLine = line == layout.lineCount - 1
|
|
495
504
|
// Only override if this is an auto-wrapped boundary
|
|
496
505
|
if (i == lineStart && textStr.getOrNull(i - 1) != '\n') {
|
|
497
506
|
isAtLineStart = true
|
|
@@ -517,7 +526,9 @@ class HighlightTextView : AppCompatEditText {
|
|
|
517
526
|
backgroundInsetRight,
|
|
518
527
|
radius,
|
|
519
528
|
isAtLineStart,
|
|
520
|
-
isAtLineEnd
|
|
529
|
+
isAtLineEnd,
|
|
530
|
+
isOnFirstLine,
|
|
531
|
+
isOnLastLine
|
|
521
532
|
)
|
|
522
533
|
editable.setSpan(span, i, i + 1, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE)
|
|
523
534
|
}
|
|
@@ -590,12 +601,19 @@ class HighlightTextView : AppCompatEditText {
|
|
|
590
601
|
var isAtLineStart = i == 0 || hasNewlineBefore
|
|
591
602
|
var isAtLineEnd = i == textStr.length - 1 || hasNewlineAfter
|
|
592
603
|
|
|
604
|
+
// Determine if this is the first or last line
|
|
605
|
+
var isOnFirstLine = i == 0 || hasNewlineBefore
|
|
606
|
+
var isOnLastLine = i == textStr.length - 1 || hasNewlineAfter
|
|
607
|
+
|
|
593
608
|
// Only use layout for auto-wrapped lines (not manual newlines)
|
|
594
609
|
if (!hasNewlineBefore && !hasNewlineAfter && layoutObj != null && i < textStr.length) {
|
|
595
610
|
try {
|
|
596
611
|
val line = layoutObj.getLineForOffset(i)
|
|
597
612
|
val lineStart = layoutObj.getLineStart(line)
|
|
598
613
|
val lineEnd = layoutObj.getLineEnd(line)
|
|
614
|
+
// Check if this is the first or last line
|
|
615
|
+
isOnFirstLine = line == 0
|
|
616
|
+
isOnLastLine = line == layoutObj.lineCount - 1
|
|
599
617
|
// Only override if this is an auto-wrapped boundary
|
|
600
618
|
if (i == lineStart && textStr.getOrNull(i - 1) != '\n') {
|
|
601
619
|
isAtLineStart = true
|
|
@@ -621,13 +639,23 @@ class HighlightTextView : AppCompatEditText {
|
|
|
621
639
|
backgroundInsetRight,
|
|
622
640
|
radius,
|
|
623
641
|
isAtLineStart,
|
|
624
|
-
isAtLineEnd
|
|
642
|
+
isAtLineEnd,
|
|
643
|
+
isOnFirstLine,
|
|
644
|
+
isOnLastLine
|
|
625
645
|
)
|
|
626
646
|
editable.setSpan(span, i, i + 1, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE)
|
|
627
647
|
}
|
|
628
648
|
}
|
|
629
649
|
|
|
630
650
|
isUpdatingText = false
|
|
651
|
+
|
|
652
|
+
// Schedule a post-layout update to ensure corner rounding is correct
|
|
653
|
+
// This is needed because layout might not be ready when this method is called
|
|
654
|
+
post {
|
|
655
|
+
if (!isUpdatingText) {
|
|
656
|
+
updateAutoWrappedLineBoundaries()
|
|
657
|
+
}
|
|
658
|
+
}
|
|
631
659
|
}
|
|
632
660
|
|
|
633
661
|
/**
|
|
@@ -668,12 +696,17 @@ class HighlightTextView : AppCompatEditText {
|
|
|
668
696
|
val isAtLineStart = spanStart == lineStart
|
|
669
697
|
val isAtLineEnd = spanEnd == lineEnd
|
|
670
698
|
|
|
699
|
+
// Check if this is the first or last line
|
|
700
|
+
val isOnFirstLine = line == 0
|
|
701
|
+
val isOnLastLine = line == layout.lineCount - 1
|
|
702
|
+
|
|
671
703
|
// Only update if this is an auto-wrapped line boundary (not a newline boundary)
|
|
672
704
|
val isNewlineBoundary = (spanStart > 0 && textStr[spanStart - 1] == '\n') ||
|
|
673
705
|
(spanEnd < textStr.length && textStr[spanEnd] == '\n')
|
|
674
706
|
|
|
675
707
|
// Only recreate span if it's at an auto-wrapped boundary and flags are wrong
|
|
676
|
-
if (!isNewlineBoundary && (isAtLineStart != span.isLineStart || isAtLineEnd != span.isLineEnd
|
|
708
|
+
if (!isNewlineBoundary && (isAtLineStart != span.isLineStart || isAtLineEnd != span.isLineEnd ||
|
|
709
|
+
isOnFirstLine != span.isFirstLine || isOnLastLine != span.isLastLine)) {
|
|
677
710
|
val newSpan = RoundedBackgroundSpan(
|
|
678
711
|
span.backgroundColor,
|
|
679
712
|
span.textColor,
|
|
@@ -687,7 +720,9 @@ class HighlightTextView : AppCompatEditText {
|
|
|
687
720
|
span.backgroundInsetRight,
|
|
688
721
|
span.cornerRadius,
|
|
689
722
|
isAtLineStart,
|
|
690
|
-
isAtLineEnd
|
|
723
|
+
isAtLineEnd,
|
|
724
|
+
isOnFirstLine,
|
|
725
|
+
isOnLastLine
|
|
691
726
|
)
|
|
692
727
|
editable.removeSpan(span)
|
|
693
728
|
editable.setSpan(newSpan, spanStart, spanEnd, Spannable.SPAN_EXCLUSIVE_EXCLUSIVE)
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "react-native-highlight-text-view",
|
|
3
|
-
"version": "0.1.
|
|
3
|
+
"version": "0.1.24",
|
|
4
4
|
"description": "A native text input for React Native that supports inline text highlighting",
|
|
5
5
|
"main": "./lib/module/index.js",
|
|
6
6
|
"types": "./lib/typescript/src/index.d.ts",
|