Skip to content

Commit b3d4d01

Browse files
authored
Fabric : Implements selectable prop for <Text> (#15473)
* visual studio 2026 strict check fix * Implement text selection with drag highlight for selectable prop * implemented copy to clipboard * CTRL + A to select all text * Double-click on a word in selectable text selects the word * right click on selected text provides context menu * fixes unselect after CTRL + A selection * implements I-beam cursor for selectable text * default selection color cleanup * yarn lint:fix and format * Change files * nit * nit * review comments ( double click , theme ( use of system api) , Capture pointer ) * removed weak_ref of ComponentView rather take ReactTaggedView * yarn format * review comments * nit * review comments : nit * invalid/null tag returns -1 for ReactTaggedView * support CJK selcetion using icu.h * update Desktop.DLL with icu.lib * CJK word boundary using dictionary * review comments * yarn lint:fix and format * Add IcuUtils.cpp to project files for CJK support * remove ICUUtils from Microsoft.ReactNative.vcxproj already added to shared
1 parent 1071c00 commit b3d4d01

File tree

16 files changed

+827
-5
lines changed

16 files changed

+827
-5
lines changed
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
{
2+
"type": "prerelease",
3+
"comment": "Implements selectable for <Text>",
4+
"packageName": "react-native-windows",
5+
"email": "[email protected]",
6+
"dependentChangeType": "patch"
7+
}

packages/playground/Samples/text.tsx

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,23 @@ export default class Bootstrap extends React.Component {
2020
selectable={true}>
2121
Click here : This is a text with a tooltip.
2222
</Text>
23+
24+
<View style={styles.selectionTestContainer}>
25+
<Text style={styles.sectionTitle}>Text Selection Test</Text>
26+
<Text selectable={true} style={styles.selectableText}>
27+
This text is SELECTABLE. Try clicking and dragging to select it.
28+
</Text>
29+
<Text selectable={true} style={styles.selectableText}>
30+
Hello 世界世界 World - Double-click to test CJK word selection!
31+
</Text>
32+
<Text selectable={false} style={styles.nonSelectableText}>
33+
This text is NOT selectable (selectable=false).
34+
</Text>
35+
<Text style={styles.defaultText}>
36+
This text has no selectable prop (default behavior).
37+
</Text>
38+
</View>
39+
2340
<View
2441
style={styles.container2}
2542
accessible={true}
@@ -64,6 +81,38 @@ const styles = StyleSheet.create({
6481
textAlign: 'center',
6582
margin: 10,
6683
},
84+
selectionTestContainer: {
85+
backgroundColor: '#f0f0f0',
86+
padding: 15,
87+
marginVertical: 10,
88+
borderRadius: 8,
89+
width: 400,
90+
},
91+
sectionTitle: {
92+
fontSize: 18,
93+
fontWeight: 'bold',
94+
marginBottom: 10,
95+
color: '#333',
96+
},
97+
selectableText: {
98+
fontSize: 16,
99+
color: '#007ACC',
100+
marginBottom: 8,
101+
padding: 8,
102+
backgroundColor: '#e8f4fc',
103+
},
104+
nonSelectableText: {
105+
fontSize: 16,
106+
color: '#666',
107+
marginBottom: 8,
108+
padding: 8,
109+
backgroundColor: '#f5f5f5',
110+
},
111+
defaultText: {
112+
fontSize: 16,
113+
color: '#999',
114+
padding: 8,
115+
},
67116
});
68117

69118
AppRegistry.registerComponent('Bootstrap', () => Bootstrap);

vnext/Desktop.DLL/React.Windows.Desktop.DLL.vcxproj

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -110,6 +110,7 @@
110110
windowscodecs.lib;
111111
WindowsApp_downlevel.lib;
112112
dxguid.lib;
113+
icu.lib;
113114
%(AdditionalDependencies)
114115
</AdditionalDependencies>
115116
<AdditionalDependencies Condition="'$(Platform)' == 'ARM64EC'">

vnext/Microsoft.ReactNative/Fabric/Composition/CompositionEventHandler.cpp

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
#include <winrt/Windows.UI.Input.h>
1616
#include "Composition.Input.h"
1717
#include "CompositionViewComponentView.h"
18+
#include "ParagraphComponentView.h"
1819
#include "ReactNativeIsland.h"
1920
#include "RootComponentView.h"
2021

@@ -1095,6 +1096,13 @@ void CompositionEventHandler::onPointerExited(
10951096
void CompositionEventHandler::onPointerPressed(
10961097
const winrt::Microsoft::ReactNative::Composition::Input::PointerPoint &pointerPoint,
10971098
winrt::Windows::System::VirtualKeyModifiers keyModifiers) noexcept {
1099+
namespace Composition = winrt::Microsoft::ReactNative::Composition;
1100+
1101+
// Clears any active text selection when left pointer is pressed
1102+
if (pointerPoint.Properties().PointerUpdateKind() != Composition::Input::PointerUpdateKind::RightButtonPressed) {
1103+
RootComponentView().ClearCurrentTextSelection();
1104+
}
1105+
10981106
PointerId pointerId = pointerPoint.PointerId();
10991107

11001108
auto staleTouch = std::find_if(m_activeTouches.begin(), m_activeTouches.end(), [pointerId](const auto &pair) {

0 commit comments

Comments
 (0)