@@ -48,15 +48,15 @@ open class NSAttributedString: NSObject, NSCopying, NSMutableCopying, NSSecureCo
48
48
}
49
49
50
50
open func copy( with zone: NSZone ? = nil ) -> Any {
51
- NSUnimplemented ( )
51
+ return self
52
52
}
53
53
54
54
open override func mutableCopy( ) -> Any {
55
55
return mutableCopy ( with: nil )
56
56
}
57
57
58
58
open func mutableCopy( with zone: NSZone ? = nil ) -> Any {
59
- NSUnimplemented ( )
59
+ return NSMutableAttributedString ( attributedString : self )
60
60
}
61
61
62
62
/// The character contents of the receiver as an NSString object.
@@ -88,7 +88,10 @@ open class NSAttributedString: NSObject, NSCopying, NSMutableCopying, NSSecureCo
88
88
}
89
89
90
90
/// Returns an NSAttributedString object consisting of the characters and attributes within a given range in the receiver.
91
- open func attributedSubstring( from range: NSRange ) -> NSAttributedString { NSUnimplemented ( ) }
91
+ open func attributedSubstring( from range: NSRange ) -> NSAttributedString {
92
+ let attributedSubstring = CFAttributedStringCreateWithSubstring ( kCFAllocatorDefault, _cfObject, CFRange ( range) )
93
+ return unsafeBitCast ( attributedSubstring, to: NSAttributedString . self)
94
+ }
92
95
93
96
/// Returns the attributes for the character at a given index, and by reference the range over which the attributes apply.
94
97
open func attributes( at location: Int , longestEffectiveRange range: NSRangePointer ? , in rangeLimit: NSRange ) -> [ NSAttributedStringKey : Any ] {
@@ -109,7 +112,17 @@ open class NSAttributedString: NSObject, NSCopying, NSMutableCopying, NSSecureCo
109
112
}
110
113
111
114
/// Returns a Boolean value that indicates whether the receiver is equal to another given attributed string.
112
- open func isEqual( to other: NSAttributedString ) -> Bool { NSUnimplemented ( ) }
115
+ open func isEqual( to other: NSAttributedString ) -> Bool {
116
+ guard let runtimeClass = _CFRuntimeGetClassWithTypeID ( CFAttributedStringGetTypeID ( ) ) else {
117
+ fatalError ( " Could not obtain CFRuntimeClass of CFAttributedString " )
118
+ }
119
+
120
+ guard let equalFunction = runtimeClass. pointee. equal else {
121
+ fatalError ( " Could not obtain equal function from CFRuntimeClass of CFAttributedString " )
122
+ }
123
+
124
+ return equalFunction ( _cfObject, other. _cfObject) == true
125
+ }
113
126
114
127
/// Returns an NSAttributedString object initialized with the characters of a given string and no attribute information.
115
128
public init ( string: String ) {
@@ -131,7 +144,13 @@ open class NSAttributedString: NSObject, NSCopying, NSMutableCopying, NSSecureCo
131
144
132
145
/// Returns an NSAttributedString object initialized with the characters and attributes of another given attributed string.
133
146
public init ( attributedString: NSAttributedString ) {
134
- NSUnimplemented ( )
147
+ // create an empty mutable attr string then immediately replace all of its contents
148
+ let mutableAttributedString = NSMutableAttributedString ( string: " " )
149
+ mutableAttributedString. setAttributedString ( attributedString)
150
+
151
+ // use the resulting _string and _attributeArray to initialize a new instance
152
+ _string = mutableAttributedString. _string
153
+ _attributeArray = mutableAttributedString. _attributeArray
135
154
}
136
155
137
156
/// Executes the block for each attribute in the range.
@@ -306,8 +325,17 @@ extension NSAttributedString {
306
325
307
326
open class NSMutableAttributedString : NSAttributedString {
308
327
309
- open func replaceCharacters( in range: NSRange , with str: String ) { NSUnimplemented ( ) }
310
- open func setAttributes( _ attrs: [ NSAttributedStringKey : Any ] ? , range: NSRange ) { NSUnimplemented ( ) }
328
+ open func replaceCharacters( in range: NSRange , with str: String ) {
329
+ CFAttributedStringReplaceString ( _cfMutableObject, CFRange ( range) , str. _cfObject)
330
+ }
331
+
332
+ open func setAttributes( _ attrs: [ NSAttributedStringKey : Any ] ? , range: NSRange ) {
333
+ guard let attrs = attrs else {
334
+ CFAttributedStringSetAttributes ( _cfMutableObject, CFRange ( range) , nil , true )
335
+ return
336
+ }
337
+ CFAttributedStringSetAttributes ( _cfMutableObject, CFRange ( range) , attributesCFDictionary ( from: attrs) , true )
338
+ }
311
339
312
340
open var mutableString : NSMutableString {
313
341
return _string as! NSMutableString
@@ -317,22 +345,64 @@ open class NSMutableAttributedString : NSAttributedString {
317
345
CFAttributedStringSetAttribute ( _cfMutableObject, CFRange ( range) , name. rawValue. _cfObject, _SwiftValue. store ( value) )
318
346
}
319
347
320
- open func addAttributes( _ attrs: [ NSAttributedStringKey : Any ] , range: NSRange ) { NSUnimplemented ( ) }
348
+ open func addAttributes( _ attrs: [ NSAttributedStringKey : Any ] , range: NSRange ) {
349
+ CFAttributedStringSetAttributes ( _cfMutableObject, CFRange ( range) , attributesCFDictionary ( from: attrs) , false )
350
+ }
351
+
352
+ open func removeAttribute( _ name: NSAttributedStringKey , range: NSRange ) {
353
+ CFAttributedStringRemoveAttribute ( _cfMutableObject, CFRange ( range) , name. rawValue. _cfObject)
354
+ }
355
+
356
+ open func replaceCharacters( in range: NSRange , with attrString: NSAttributedString ) {
357
+ CFAttributedStringReplaceAttributedString ( _cfMutableObject, CFRange ( range) , attrString. _cfObject)
358
+ }
321
359
322
- open func removeAttribute( _ name: NSAttributedStringKey , range: NSRange ) { NSUnimplemented ( ) }
360
+ open func insert( _ attrString: NSAttributedString , at loc: Int ) {
361
+ let insertRange = NSRange ( location: loc, length: 0 )
362
+ replaceCharacters ( in: insertRange, with: attrString)
363
+ }
364
+
365
+ open func append( _ attrString: NSAttributedString ) {
366
+ let appendRange = NSRange ( location: length, length: 0 )
367
+ replaceCharacters ( in: appendRange, with: attrString)
368
+ }
369
+
370
+ open func deleteCharacters( in range: NSRange ) {
371
+ // To delete a range of the attributed string, call CFAttributedStringReplaceString() with empty string and specified range
372
+ let emptyString = " " . _cfObject
373
+ CFAttributedStringReplaceString ( _cfMutableObject, CFRange ( range) , emptyString)
374
+ }
375
+
376
+ open func setAttributedString( _ attrString: NSAttributedString ) {
377
+ let fullStringRange = NSRange ( location: 0 , length: length)
378
+ replaceCharacters ( in: fullStringRange, with: attrString)
379
+ }
380
+
381
+ open func beginEditing( ) {
382
+ CFAttributedStringBeginEditing ( _cfMutableObject)
383
+ }
384
+
385
+ open func endEditing( ) {
386
+ CFAttributedStringEndEditing ( _cfMutableObject)
387
+ }
323
388
324
- open func replaceCharacters( in range: NSRange , with attrString: NSAttributedString ) { NSUnimplemented ( ) }
325
- open func insert( _ attrString: NSAttributedString , at loc: Int ) { NSUnimplemented ( ) }
326
- open func append( _ attrString: NSAttributedString ) { NSUnimplemented ( ) }
327
- open func deleteCharacters( in range: NSRange ) { NSUnimplemented ( ) }
328
- open func setAttributedString( _ attrString: NSAttributedString ) { NSUnimplemented ( ) }
389
+ open override func copy( with zone: NSZone ? = nil ) -> Any {
390
+ return NSAttributedString ( attributedString: self )
391
+ }
329
392
330
- open func beginEditing( ) { NSUnimplemented ( ) }
331
- open func endEditing( ) { NSUnimplemented ( ) }
393
+ public override init ( string: String ) {
394
+ super. init ( string: string)
395
+ _string = NSMutableString ( string: string)
396
+ }
397
+
398
+ public override init ( string: String , attributes attrs: [ NSAttributedStringKey : Any ] ? = nil ) {
399
+ super. init ( string: string, attributes: attrs)
400
+ _string = NSMutableString ( string: string)
401
+ }
332
402
333
- public override init ( string str : String ) {
334
- super. init ( string : str )
335
- _string = NSMutableString ( string: str )
403
+ public override init ( attributedString : NSAttributedString ) {
404
+ super. init ( attributedString : attributedString )
405
+ _string = NSMutableString ( string: attributedString . string )
336
406
}
337
407
338
408
public required init ? ( coder aDecoder: NSCoder ) {
@@ -344,3 +414,14 @@ open class NSMutableAttributedString : NSAttributedString {
344
414
extension NSMutableAttributedString {
345
415
internal var _cfMutableObject : CFMutableAttributedString { return unsafeBitCast ( self , to: CFMutableAttributedString . self) }
346
416
}
417
+
418
+ private extension NSMutableAttributedString {
419
+
420
+ func attributesCFDictionary( from attrs: [ NSAttributedStringKey : Any ] ) -> CFDictionary {
421
+ var attributesDictionary = [ String : Any] ( )
422
+ for (key, value) in attrs {
423
+ attributesDictionary [ key. rawValue] = value
424
+ }
425
+ return attributesDictionary. _cfObject
426
+ }
427
+ }
0 commit comments