Kotlin-Multiplatform 中的 CPointer
CPointer in Kotlin-Multiplatform
我找不到任何关于如何在 Kotlin Multiplatform 中获取 CPointer 的示例,现有的文档也没有多大帮助。
在我的 iOS 源集中,我需要构建与以下 Swift 代码等效的 Kotlin(仅包括代码的相关部分):
...(hex: String) {
if hex.hasPrefix("#") {
let start = hex.index(hex.startIndex, offsetBy: 1)
let scanner = Scanner(string: hexColor)
var hexNumber: UInt64 = 0
if scanner.scanHexInt64(&hexNumber) {
r = CGFloat((hexNumber & 0xff000000) >> 24) / 255
....
我遇到问题的具体部分是
scanner.scanHexInt64(&hexNumber)
这是 Kotlin 代码和问题
//input to function - hex: String
val scanner = NSScanner(hex)
if (hex.startsWith("#")) {
scanner.scanLocation = 1u
}
var hexNumber : UInt32 = 0u
/*Type mismatch.
Required:
CPointer<UIntVar /* = UIntVarOf<UInt> */>?
Found:
UInt32 /* = UInt */
*/
//HOW TO GET CPOINTER TO hexNumber?
scanner.scanHexInt(hexNumber)
根据文档:(link)
Pointers and arrays are mapped to CPointer<T>?.
但是如何呢?
找到了我的问题的答案。必须使用
memScoped
。
memScoped {
var pointed : UIntVar = alloc<UIntVar>()
scanner.scanHexInt(pointed.ptr)
val alpha: CGFloat = 1.0
val pointedValue = pointed.value
val r: CGFloat = (((pointedValue and 0xFF0000) shr 16)/255.0)
....
}
互联网上关于此的唯一来源(关于应用它来获取指针)在这里 - link
inline fun <R> memScoped(block: MemScope.() -> R): R
Runs given block providing allocation of memory which will be automatically disposed at the end of this scope
其中,使用扩展函数alloc()得到CVariable
fun <reified T : CVariable> NativePlacement.alloc(): T
然后您可以通过另一个扩展函数访问指针
val <T : CPointed> T.ptr: CPointer<T>
回想起来一切都非常清楚,并且清楚原来以错误的方式解决了问题,希望通过类似CPointer<UInt> = ...
的方式获得指针
https://kotlinlang.org/docs/reference/native/c_interop.html
的官方文档
import kotlinx.cinterop.UIntVar
import kotlinx.cinterop.memScoped
import kotlinx.cinterop.ptr
import platform.CoreGraphics.CGFloat
import platform.Foundation.NSScanner
import platform.Foundation.scanHexInt
import platform.UIKit.UIColor
import kotlinx.cinterop.alloc
import kotlinx.cinterop.value
fun hexToUIColor(hexStr: String): UIColor {
var cString: String = hexStr.toUpperCase()
if (cString.startsWith("#")) {
cString = cString.removePrefix("#")
}
if (cString.length != 8) {
return UIColor.grayColor
}
var a: UInt
var r: UInt
var g: UInt
var b: UInt
memScoped {
val scanner = NSScanner(cString)
var pointed : UIntVar = alloc<UIntVar>()
scanner.scanHexInt(pointed.ptr)
val alpha: CGFloat = 1.0
val pointedValue: UInt = pointed.value
a = ((pointedValue and 4278190080u) shl 24) / 255u
r = ((pointedValue and 16711680u) shl 16) / 255u
g = ((pointedValue and 65280u) shl 8) / 255u
b = ((pointedValue and 255u) shl 0) / 255u
return UIColor(red = r.toDouble(), green = g.toDouble(), blue = b.toDouble(), alpha = a.toDouble())
}
}
我找不到任何关于如何在 Kotlin Multiplatform 中获取 CPointer 的示例,现有的文档也没有多大帮助。 在我的 iOS 源集中,我需要构建与以下 Swift 代码等效的 Kotlin(仅包括代码的相关部分):
...(hex: String) {
if hex.hasPrefix("#") {
let start = hex.index(hex.startIndex, offsetBy: 1)
let scanner = Scanner(string: hexColor)
var hexNumber: UInt64 = 0
if scanner.scanHexInt64(&hexNumber) {
r = CGFloat((hexNumber & 0xff000000) >> 24) / 255
....
我遇到问题的具体部分是
scanner.scanHexInt64(&hexNumber)
这是 Kotlin 代码和问题
//input to function - hex: String
val scanner = NSScanner(hex)
if (hex.startsWith("#")) {
scanner.scanLocation = 1u
}
var hexNumber : UInt32 = 0u
/*Type mismatch.
Required:
CPointer<UIntVar /* = UIntVarOf<UInt> */>?
Found:
UInt32 /* = UInt */
*/
//HOW TO GET CPOINTER TO hexNumber?
scanner.scanHexInt(hexNumber)
根据文档:(link)
Pointers and arrays are mapped to
CPointer<T>?.
但是如何呢?
找到了我的问题的答案。必须使用
memScoped
。
memScoped {
var pointed : UIntVar = alloc<UIntVar>()
scanner.scanHexInt(pointed.ptr)
val alpha: CGFloat = 1.0
val pointedValue = pointed.value
val r: CGFloat = (((pointedValue and 0xFF0000) shr 16)/255.0)
....
}
互联网上关于此的唯一来源(关于应用它来获取指针)在这里 - link
inline fun <R> memScoped(block: MemScope.() -> R): R
Runs given block providing allocation of memory which will be automatically disposed at the end of this scope
其中,使用扩展函数alloc()得到CVariable
fun <reified T : CVariable> NativePlacement.alloc(): T
然后您可以通过另一个扩展函数访问指针
val <T : CPointed> T.ptr: CPointer<T>
回想起来一切都非常清楚,并且清楚原来以错误的方式解决了问题,希望通过类似CPointer<UInt> = ...
的方式获得指针
https://kotlinlang.org/docs/reference/native/c_interop.html
import kotlinx.cinterop.UIntVar
import kotlinx.cinterop.memScoped
import kotlinx.cinterop.ptr
import platform.CoreGraphics.CGFloat
import platform.Foundation.NSScanner
import platform.Foundation.scanHexInt
import platform.UIKit.UIColor
import kotlinx.cinterop.alloc
import kotlinx.cinterop.value
fun hexToUIColor(hexStr: String): UIColor {
var cString: String = hexStr.toUpperCase()
if (cString.startsWith("#")) {
cString = cString.removePrefix("#")
}
if (cString.length != 8) {
return UIColor.grayColor
}
var a: UInt
var r: UInt
var g: UInt
var b: UInt
memScoped {
val scanner = NSScanner(cString)
var pointed : UIntVar = alloc<UIntVar>()
scanner.scanHexInt(pointed.ptr)
val alpha: CGFloat = 1.0
val pointedValue: UInt = pointed.value
a = ((pointedValue and 4278190080u) shl 24) / 255u
r = ((pointedValue and 16711680u) shl 16) / 255u
g = ((pointedValue and 65280u) shl 8) / 255u
b = ((pointedValue and 255u) shl 0) / 255u
return UIColor(red = r.toDouble(), green = g.toDouble(), blue = b.toDouble(), alpha = a.toDouble())
}
}