2
0
mirror of https://github.com/esiur/esiur-dart.git synced 2025-05-06 04:02:57 +00:00
2021-07-14 05:16:40 +03:00

523 lines
12 KiB
Dart

/*
* Copyright (c) 2019 Ahmed Kh. Zamil
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
import 'dart:typed_data';
import 'dart:convert';
import 'BinaryList.dart';
import 'dart:collection';
import 'Guid.dart';
/**
* Created by Ahmed Zamil on 6/10/2019.
*/
const UNIX_EPOCH = 621355968000000000;
const TWO_PWR_32 = (1 << 16) * (1 << 16);
class DC with IterableMixin<int> {
Uint8List _data;
ByteData _dv;
DC(int length) {
_data = new Uint8List(length);
_dv = ByteData.view(_data.buffer);
}
DC.fromUint8Array(Uint8List array) {
_data = array;
_dv = ByteData.view(_data.buffer);
}
DC.fromList(List<int> list) {
_data = Uint8List.fromList(list);
_dv = ByteData.view(_data.buffer);
}
int operator [](int index) => _data[index];
operator []=(int index, int value) => _data[index] = value;
int get length => _data.length;
Iterator<int> get iterator => _data.iterator;
static DC hexToBytes(String value) {
// convert hex to Uint8Array
var rt = new DC(value.length ~/ 2);
for (var i = 0; i < rt.length; i++)
rt[i] = int.parse(value.substring(i * 2, 2), radix: 16);
return rt;
}
static DC boolToBytes(value) {
var rt = new DC(1);
rt.setBoolean(0, value);
return rt;
}
static DC guidToBytes(Guid value) {
var rt = new DC(16);
rt.setGuid(0, value);
return rt;
}
static DC guidArrayToBytes(List<Guid> value) {
var rt = new DC(value.length * 16);
for (var i = 0; i < value.length; i++) rt.setGuid(i * 16, value[i]);
return rt;
}
static DC boolArrayToBytes(List<bool> value) {
var rt = new DC(value.length);
for (var i = 0; i < value.length; i++) rt[i] = value[i] ? 1 : 0;
return rt;
}
static DC int8ToBytes(value) {
var rt = new DC(1);
rt.setInt8(0, value);
return rt;
}
static DC int8ArrayToBytes(Int8List value) {
var rt = new DC(value.length);
for (var i = 0; i < value.length; i++) rt.setInt8(i, value[i]);
return rt;
}
static DC uint8ToBytes(value) {
var rt = new DC(1);
rt.setUint8(0, value);
return rt;
}
static DC uint8ArrayToBytes(Uint8List value) {
var rt = new DC(value.length);
for (var i = 0; i < value.length; i++) rt.setUint8(i, value[i]);
return rt;
}
static DC charToBytes(int value) {
var rt = new DC(2);
rt.setChar(0, value);
return rt;
}
static DC charArrayToBytes(Uint16List value) {
var rt = new DC(value.length * 2);
for (var i = 0; i < value.length; i++) rt.setChar(i * 2, value[i]);
return rt;
}
static DC int16ToBytes(int value) {
var rt = new DC(2);
rt.setInt16(0, value);
return rt;
}
static DC int16ArrayToBytes(List<int> value) {
var rt = new DC(value.length * 2);
for (var i = 0; i < value.length; i++) rt.setInt16(i * 2, value[i]);
return rt;
}
static DC uint16ToBytes(int value) {
var rt = new DC(2);
rt.setUint16(0, value);
return rt;
}
static DC uint16ArrayToBytes(Uint16List value) {
var rt = new DC(value.length * 2);
for (var i = 0; i < value.length; i++) rt.setUint16(i * 2, value[i]);
return rt;
}
static DC int32ToBytes(int value) {
var rt = new DC(4);
rt.setInt32(0, value);
return rt;
}
static DC int32ArrayToBytes(Int32List value) {
var rt = new DC(value.length * 4);
for (var i = 0; i < value.length; i++) rt.setInt32(i * 4, value[i]);
return rt;
}
static DC uint32ToBytes(int value) {
var rt = new DC(4);
rt.setUint32(0, value);
return rt;
}
static DC uint32ArrayToBytes(Uint32List value) {
var rt = new DC(value.length * 4);
for (var i = 0; i < value.length; i++) rt.setUint32(i * 4, value[i]);
return rt;
}
static DC float32ToBytes(double value) {
var rt = new DC(4);
rt.setFloat32(0, value);
return rt;
}
static DC float32ArrayToBytes(Float32List value) {
var rt = new DC(value.length * 4);
for (var i = 0; i < value.length; i++) rt.setFloat32(i * 4, value[i]);
return rt;
}
static DC int64ToBytes(int value) {
var rt = new DC(8);
rt.setInt64(0, value);
return rt;
}
static DC int64ArrayToBytes(Int64List value) {
var rt = new DC(value.length * 8);
for (var i = 0; i < value.length; i++) rt.setInt64(i * 8, value[i]);
return rt;
}
static DC uint64ToBytes(int value) {
var rt = new DC(8);
rt.setUint64(0, value);
return rt;
}
static DC uint64ArrayToBytes(Uint64List value) {
var rt = new DC(value.length * 8);
for (var i = 0; i < value.length; i++) rt.setUint64(i * 8, value[i]);
return rt;
}
static DC float64ToBytes(double value) {
var rt = new DC(8);
rt.setFloat64(0, value);
return rt;
}
static DC float64ArrayToBytes(Float64List value) {
var rt = new DC(value.length * 8);
for (var i = 0; i < value.length; i++) rt.setFloat64(i * 8, value[i]);
return rt;
}
static DC dateTimeToBytes(DateTime value) {
var rt = new DC(8);
rt.setDateTime(0, value);
return rt;
}
static DC dateTimeArrayToBytes(List<DateTime> value) {
var rt = new DC(value.length * 8);
for (var i = 0; i < value.length; i++) rt.setDateTime(i * 8, value[i]);
return rt;
}
static DC stringToBytes(String value) {
var bytes = utf8.encode(value);
var rt = new DC.fromList(bytes);
return rt;
}
static DC stringArrayToBytes(List<String> value) {
var list = new BinaryList();
for (var i = 0; i < value.length; i++) {
var s = DC.stringToBytes(value[i]);
list.addUint32(s.length).addUint8Array(s.toArray());
}
return list.toDC();
}
DC append(DC src, int offset, int length) {
//if (!(src is DC))
// src = new DC(src);
var appendix = src.clip(offset, length);
var rt = new DC(this.length + appendix.length);
rt.set(this, 0);
rt.set(appendix, this.length);
this._data = rt._data;
this._dv = rt._dv;
return this;
}
set(DC dc, int offset) {
_data.setRange(offset, offset + dc.length, dc._data);
}
static combine(a, aOffset, aLength, b, bOffset, bLength) {
if (!(a is DC)) a = new DC(a);
if (!(b is DC)) b = new DC(b);
a = a.clip(aOffset, aLength);
b = b.clip(bOffset, bLength);
var rt = new DC(a.length + b.length);
rt.set(a, 0);
rt.set(b, a.length);
return rt;
}
DC clip(offset, length) {
return DC.fromUint8Array(
Uint8List.fromList(_data.getRange(offset, offset + length).toList()));
}
getInt8(int offset) {
return _dv.getInt8(offset);
}
getUint8(int offset) {
return _data[offset]; // this.dv.getUint8(offset);
}
getInt16(int offset) {
return _dv.getInt16(offset);
}
getUint16(int offset) {
return _dv.getUint16(offset);
}
getInt32(int offset) {
return _dv.getInt32(offset);
}
getUint32(int offset) {
return _dv.getUint32(offset);
}
getFloat32(int offset) {
return _dv.getFloat32(offset);
}
getFloat64(int offset) {
return _dv.getFloat64(offset);
}
setInt8(int offset, int value) {
return _dv.setInt8(offset, value);
}
setUint8(int offset, int value) {
return _dv.setUint8(offset, value);
}
setInt16(int offset, int value) {
return _dv.setInt16(offset, value);
}
setUint16(int offset, int value) {
return _dv.setUint16(offset, value);
}
setInt32(int offset, int value) {
return _dv.setInt32(offset, value);
}
setUint32(int offset, int value) {
return _dv.setUint32(offset, value);
}
setFloat32(int offset, double value) {
return _dv.setFloat32(offset, value);
}
setFloat64(int offset, double value) {
return _dv.setFloat64(offset, value);
}
Int8List getInt8Array(int offset, int length) {
return _data.buffer.asInt8List(offset, length);
}
Uint8List getUint8Array(int offset, int length) {
return _data.buffer.asUint8List(offset, length);
}
Int16List getInt16Array(int offset, int length) {
return _data.buffer.asInt16List(offset, length);
}
Uint16List getUint16Array(int offset, int length) {
return _data.buffer.asUint16List(offset, length);
}
Int32List getInt32Array(int offset, int length) {
return _data.buffer.asInt32List(offset, length);
}
Uint32List getUint32Array(int offset, int length) {
return _data.buffer.asUint32List(offset, length);
}
Float32List getFloat32Array(int offset, int length) {
return _data.buffer.asFloat32List(offset, length);
}
Float64List getFloat64Array(int offset, int length) {
return _data.buffer.asFloat64List(offset, length);
}
Int64List getInt64Array(int offset, int length) {
return _data.buffer.asInt64List(offset, length);
}
Uint64List getUint64Array(int offset, int length) {
return _data.buffer.asUint64List(offset, length);
}
bool getBoolean(int offset) {
return this.getUint8(offset) > 0;
}
setBoolean(int offset, bool value) {
this.setUint8(offset, value ? 1 : 0);
}
List<bool> getBooleanArray(int offset, int length) {
List<bool> rt = [];
for (var i = 0; i < length; i++) rt.add(this.getBoolean(offset + i));
return rt;
}
String getChar(int offset) {
return String.fromCharCode(this.getUint16(offset));
}
setChar(int offset, int value) {
this.setUint16(offset, value); //value.codeUnitAt(0));
}
List<String> getCharArray(int offset, int length) {
List<String> rt = [];
for (var i = 0; i < length; i += 2) rt.add(this.getChar(offset + i));
return rt;
}
String getHex(offset, length) {
var rt = "";
for (var i = offset; i < offset + length; i++) {
var h = _data[i].toRadixString(16);
rt += h.length == 1 ? "0" + h : h;
}
return rt;
}
/*
List<T> toList<T>(offset, length)
{
var rt = new List<T>();
for(var i = 0; i < length; i++)
rt[i] = _data[offset+i] as T;
return rt;
}*/
Uint8List toArray() => _data;
String getString(offset, length) {
var bytes = clip(offset, length)._data; // toList(offset, length);
var str = utf8.decode(bytes);
return str;
}
List<String> getStringArray(offset, length) {
List<String> rt = [];
var i = 0;
while (i < length) {
var cl = this.getUint32(offset + i);
i += 4;
rt.add(this.getString(offset + i, cl));
i += cl;
}
return rt;
}
getInt64(offset) {
return _dv.getUint64(offset);
}
getUint64(offset) {
return _dv.getInt64(offset);
}
void setInt64(offset, value) {
_dv.setInt64(offset, value);
}
void setUint64(offset, value) {
_dv.setUint64(offset, value);
}
setDateTime(offset, DateTime value) {
// Unix Epoch
var ticks = UNIX_EPOCH + (value.millisecondsSinceEpoch * 10000);
this.setUint64(offset, ticks);
}
DateTime getDateTime(int offset) {
var ticks = this.getUint64(offset);
// there are 10,000 ticks in a millisecond
return DateTime.fromMillisecondsSinceEpoch((ticks - UNIX_EPOCH) ~/ 10000);
}
List<DateTime> getDateTimeArray(int offset, int length) {
List<DateTime> rt = [];
for (var i = 0; i < length; i += 8) rt.add(this.getDateTime(offset + i));
return rt;
}
Guid getGuid(int offset) {
return new Guid(this.clip(offset, 16));
}
setGuid(int offset, Guid guid) {
set(guid.value, offset);
}
List<Guid> getGuidArray(int offset, int length) {
List<Guid> rt = [];
for (var i = 0; i < length; i += 16) rt.add(this.getGuid(offset + i));
return rt;
}
bool sequenceEqual(ar) {
if (ar.length != this.length)
return false;
else {
for (var i = 0; i < this.length; i++) if (ar[i] != this[i]) return false;
}
return true;
}
}