Compare commits

..
Author SHA1 Message Date
John Colvin e9fdbc2acd ui (refactor): Consolidate (Repeat)Button colors to one class
The only difference between a RepeatButton and a regular Button is in
the click-behavior (they should look identical).
2022-12-12 11:47:20 -05:00
John Colvin a50e0cfc26 fix: Add a couple null checks 2022-12-12 11:01:01 -05:00
430 changed files with 117698 additions and 136671 deletions

No files matched your search

-129
View File
@@ -1,129 +0,0 @@
FROM ubuntu:22.04
ARG DEBIAN_FRONTEND=noninteractive
# Note installations that take a while (more than 10s)
RUN apt-get update
RUN apt-get install -y ca-certificates
RUN apt-get install -y ccache
RUN apt-get install -y curl
RUN apt-get install -y fish
RUN apt-get install -y gdb
# git-all: ~250s
RUN apt-get install -y git-all
RUN apt-get install -y gnupg
# liblttng-ust-dev: ~30s
RUN apt-get install -y liblttng-ust-dev
RUN apt-get install -y libssh2-1-dev
RUN apt-get install -y locales
RUN apt-get install -y ninja-build
# openssh-server: ~40s
RUN apt-get install -y openssh-server
RUN apt-get install -y pkg-config
RUN apt-get install -y software-properties-common
RUN apt-get install -y sudo
RUN apt-get install -y tzdata
RUN apt-get install -y vim
RUN apt-get install -y zip
# Python: ~30s
RUN apt-get install -y \
python3-pip \
python3-venv \
&& python3 -m pip install --upgrade pip
# GCC
ARG gcc_major=13
RUN \
add-apt-repository ppa:ubuntu-toolchain-r/test \
&& apt-get update \
&& apt-get install -y g++-$gcc_major
# Clang
ARG clang_major=17
RUN \
curl -fsSL https://apt.llvm.org/llvm-snapshot.gpg.key 2> /dev/null \
| gpg --dearmor - \
| tee /usr/share/keyrings/llvm-snapshot.gpg > /dev/null \
&& echo "deb [signed-by=/usr/share/keyrings/llvm-snapshot.gpg] http://apt.llvm.org/$(lsb_release -cs)/ llvm-toolchain-$(lsb_release -cs)-$clang_major main" \
| tee -a "/etc/apt/sources.list.d/llvm.list" \
&& apt-get update \
&& apt-get install -y \
clang-$clang_major \
clang-format-$clang_major \
clangd-$clang_major
# CMake
RUN \
curl -fsSL https://apt.kitware.com/keys/kitware-archive-latest.asc 2> /dev/null \
| gpg --dearmor - \
| tee /usr/share/keyrings/kitware-archive-keyring.gpg > /dev/null \
&& echo "deb [signed-by=/usr/share/keyrings/kitware-archive-keyring.gpg] https://apt.kitware.com/ubuntu/ $(lsb_release -cs) main" \
| tee /etc/apt/sources.list.d/kitware.list > /dev/null \
&& apt-get update \
&& apt-get install -y cmake
# Dotnet
RUN apt-get update && apt-get install -y dotnet7
# Node
ARG node_major=18
RUN mkdir -p /etc/apt/keyrings \
&& curl -fsSL https://deb.nodesource.com/gpgkey/nodesource-repo.gpg.key \
| gpg --dearmor -o /etc/apt/keyrings/nodesource.gpg \
&& echo "deb [signed-by=/etc/apt/keyrings/nodesource.gpg] https://deb.nodesource.com/node_$node_major.x nodistro main" \
| tee /etc/apt/sources.list.d/nodesource.list \
&& apt-get update \
&& apt-get install -y nodejs
# Emumba (deps)
RUN apt-get update && apt-get -y install rapidjson-dev
# Emumba
COPY emumba /emumba
RUN dpkg -i /emumba/emumba-deribit-connector-3.3.1-Linux.LICENSE_DISABLED.deb \
&& rm -r /emumba
# Pcap
RUN apt-get update && apt-get install -y libpcap0.8-dev
RUN apt-get update && apt-get install -y \
docker.io \
docker-compose \
docker-compose-v2
# Set up default executables (update-alternatives)
RUN \
update-alternatives --install /usr/bin/clang clang /usr/bin/clang-$clang_major 100; \
update-alternatives --install /usr/bin/clang++ clang++ /usr/bin/clang++-$clang_major 100; \
update-alternatives --install /usr/bin/clang-format clang-format /usr/bin/clang-format-$clang_major 100; \
update-alternatives --install /usr/bin/clangd clangd /usr/bin/clangd-$clang_major 100; \
update-alternatives --install /usr/bin/gcc gcc /usr/bin/gcc-$gcc_major 100; \
update-alternatives --install /usr/bin/g++ g++ /usr/bin/g++-$gcc_major 100
# Add compiler symlinks for ccache
RUN \
ln -s /usr/bin/ccache /usr/local/bin/clang; \
ln -s /usr/bin/ccache /usr/local/bin/clang++; \
ln -s /usr/bin/ccache /usr/local/bin/clang-$clang_major; \
ln -s /usr/bin/ccache /usr/local/bin/clang++-$clang_major; \
ln -s /usr/bin/ccache /usr/local/bin/gcc; \
ln -s /usr/bin/ccache /usr/local/bin/g++
RUN locale-gen en_US.UTF-8
ARG docker_user="bts"
ARG docker_uid="1000"
ARG docker_pass="bts"
RUN \
groupadd -g "$docker_uid" "$docker_user" \
&& useradd \
-m \
-u "$docker_uid" \
-g "$docker_uid" \
-G sudo \
--password "$(openssl passwd -1 "$docker_pass")" \
"$docker_user"
RUN usermod -aG docker "$docker_user"
-43
View File
@@ -1,43 +0,0 @@
{
"dockerFile": "Dockerfile",
// Creates local dir to mount to HOME in docker
"initializeCommand": "mkdir -p ${localEnv:HOME}/.bts/devcontainer-mounts/${devcontainerId}",
"hostRequirements": {
"memory": "4gb",
"storage": "6gb"
},
"postCreateCommand": "/home/bts/spark/docker/sparkd/dev/devcontainer_post_create.sh",
"containerUser": "bts",
"workspaceMount": "source=${localWorkspaceFolder},target=/home/bts/spark,type=bind",
"workspaceFolder": "/home/bts/spark",
"updateRemoteUserUID": true,
"shutdownAction": "none",
// Note: If running multiple containers on the same host, each must use a
// unique set of ports. Usually we just add 1000 to each port as needed. For
// example, if 8000-8003 is taken, go with 9000-9003, then 10000-10003, etc.
"runArgs": [
"--shm-size",
"2gb",
"--network",
"host"
],
"mounts": [
"source=${localEnv:HOME}/.bts/devcontainer-mounts/${devcontainerId},target=/home/bts,type=bind",
"source=/var/run/docker.sock,target=/var/run/docker.sock,type=bind"
],
"customizations": {
"vscode": {
"settings": {
"clangd.arguments": [
"--compile-commands-dir=${workspaceFolder}/build/clang/debug"
]
},
"extensions": [
"eamodio.gitlens",
"llvm-vs-code-extensions.vscode-clangd",
"ms-vscode.cmake-tools",
"ms-vscode.cpptools"
]
}
}
}
+1 -1
View File
@@ -42,7 +42,7 @@ trace_data/
/.ignore
*.rej
.clangd/
*CMakeDeps*.cmake
*CMakeDeps.cmake
/sniper.ipynb
/src/.clang-format
/src/server/sparkd/cmds/spartan/analysis/.ipynb_checkpoints
+6 -3
View File
@@ -1,6 +1,9 @@
[submodule "externals"]
path = externals
url = git@bitbucket.org:bluetradesys/externals.git
[submodule "vcpkg"]
path = vcpkg
url = https://github.com/microsoft/vcpkg.git
[submodule "docker/linux"]
path = docker/linux
url = git@bitbucket.org:bluetradesys/linux_docker.git
[submodule "docker/windows"]
path = docker/windows
url = git@bitbucket.org:bluetradesys/windows_docker.git
+75 -25
View File
@@ -1,6 +1,5 @@
cmake_minimum_required(VERSION 3.12)
project(spark)
set(CMAKE_CXX_STANDARD 20)
if(WIN32)
set(platform "windows")
@@ -14,49 +13,100 @@ set(
CACHE
STRING
"External dependencies root folder (should contain folders: lib, bin, include")
set(EXTERNALS_BIN "${EXTERNALS_ROOT}/bin")
set(EXTERNALS_INCLUDE "${EXTERNALS_ROOT}/include")
set(EXTERNALS_LIB "${EXTERNALS_ROOT}/lib/$<CONFIG>")
set(BUILD_DOCS OFF CACHE BOOL "Build documentation")
set(SPARK_PYTHON "${EXTERNALS_ROOT}/python")
set(SPARK_BIN "${EXTERNALS_ROOT}/bin")
set(SPARK_INCLUDE "${EXTERNALS_ROOT}/include")
set(SPARK_LIB "${EXTERNALS_ROOT}/lib/${CMAKE_BUILD_TYPE}")
set(BUILD_SDK OFF CACHE BOOL "Build the sdk")
set(EXPORT_MD_CONSUMER OFF CACHE BOOL "Export (extern) C functions for MD consumer interop")
if (WIN32)
set(BUILD_SPARKD OFF CACHE BOOL "Build sparkd")
set(BUILD_WEB OFF CACHE BOOL "Build the web server")
else()
set(BUILD_SPARKD ON CACHE BOOL "Build sparkd")
set(BUILD_WEB ON CACHE BOOL "Build the web server")
endif()
set(BUILD_WEB ON CACHE BOOL "Build the web server")
include_directories(BEFORE SYSTEM ${EXTERNALS_INCLUDE} ${EXTERNALS_ROOT}/include/zlib)
link_directories(${EXTERNALS_LIB})
include_directories(BEFORE SYSTEM ${SPARK_INCLUDE} ${EXTERNALS_ROOT}/include/zlib)
link_directories(${SPARK_LIB})
add_compile_definitions(EXPORT_MD_CONSUMER="${EXPORT_MD_CONSUMER}")
if(WIN32)
# flags
set(
CMAKE_CXX_FLAGS
"${CMAKE_CXX_FLAGS} \
/MP \
/WX /wd4251 /wd4250 /wd4251 /wd4244 /wd4267 /wd4355 /wd4275 /wd4345 \
/bigobj \
/DCURL_STATICLIB \
/D_WINSOCK_DEPRECATED_NO_WARNINGS \
/D__TBB_NO_IMPLICIT_LINKAGE \
/DBOOST_ALL_NO_LIB \
/std:c++17 \
/D_SCL_SECURE_NO_WARNINGS /D_CRT_SECURE_NO_WARNINGS /D_WIN32_WINNT=0x0600")
set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} /MTd")
set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_DEBUG} /MT")
set(
CMAKE_SHARED_LINKER_FLAGS_RELEASE
"${CMAKE_SHARED_LINKER_FLAGS_RELEASE} \
/DEBUG \
/OPT:REF \
/OPT:ICF \
/LTCG")
# subdirs
add_subdirectory(src/lib)
else()
# make sparkd look for libspark.so in its directory
set(CMAKE_BUILD_WITH_INSTALL_RPATH TRUE)
set(CMAKE_INSTALL_RPATH ".")
set(CMAKE_INSTALL_PREFIX "${CMAKE_SOURCE_DIR}/install/${CMAKE_BUILD_TYPE}/sparkd")
add_compile_definitions(SPARK_ENABLE_CCAPI)
add_compile_definitions(CCAPI_ENABLE_SERVICE_MARKET_DATA)
add_compile_definitions(CCAPI_ENABLE_SERVICE_EXECUTION_MANAGEMENT)
add_compile_definitions(CCAPI_ENABLE_EXCHANGE_FTX)
add_compile_definitions(CCAPI_ENABLE_EXCHANGE_BINANCE)
add_compile_definitions(CCAPI_ENABLE_EXCHANGE_DERIBIT)
add_compile_definitions(CCAPI_ENABLE_LOG_WARN)
# flags
set(
CMAKE_CXX_FLAGS_DEBUG
"${CMAKE_CXX_FLAGS_DEBUG} \
-fPIC \
-Wall \
-pedantic \
-Wextra \
-Werror \
-Wno-missing-braces \
-Wno-ignored-qualifiers \
--std=c++17 -fdiagnostics-color")
set(CMAKE_CXX_FLAGS_RELEASE "${CMAKE_CXX_FLAGS_DEBUG} -fno-omit-frame-pointer -DNDEBUG -O3")
set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -DDEBUG")
set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -Wno-undef")
# subdirs
if (BUILD_SPARKD)
add_subdirectory(src/server/sparkd)
add_subdirectory(src/data_files)
endif()
add_subdirectory(src/server/sparkd)
add_subdirectory(src/lib)
if (BUILD_WEB)
add_subdirectory(src/web)
endif()
if(BUILD_DOCS)
add_subdirectory(doc/user)
endif()
add_subdirectory(doc/user)
if(BUILD_SDK)
add_subdirectory(src/sdk)
endif()
add_subdirectory(src/data_files)
add_custom_command(
OUTPUT ${CMAKE_BINARY_DIR}/server
COMMAND mkdir -p ${CMAKE_BINARY_DIR}/server
COMMAND ln ARGS -sf ${CMAKE_BINARY_DIR}/src/server/sparkd/sparkd ${CMAKE_BINARY_DIR}/server
COMMAND ln ARGS -sf ${CMAKE_BINARY_DIR}/web ${CMAKE_BINARY_DIR}/server
COMMAND ln ARGS -sf ${CMAKE_BINARY_DIR}/data_files ${CMAKE_BINARY_DIR}/server
COMMAND ln ARGS -sf ${CMAKE_BINARY_DIR}/src/lib/libspark.so ${CMAKE_BINARY_DIR}/server
COMMAND
ln ARGS -sf
${EXTERNALS_ROOT}/lib/Release/libOnixS.IceImpactMulticastPriceFeedHandlerCpp.so.3.16.0.0
${CMAKE_BINARY_DIR}/server
COMMAND ln ARGS -sf ${EXTERNALS_ROOT}/lib/Release/libACE-5.7.5.so ${CMAKE_BINARY_DIR}/server
COMMAND mkdir ARGS -p ${CMAKE_BINARY_DIR}/server/plugins
COMMENT "Creating server runtime layout"
DEPENDS sparkd data_files_dir)
add_custom_target(server_layout ALL DEPENDS ${CMAKE_BINARY_DIR}/server)
install(FILES "${CMAKE_SOURCE_DIR}/externals/linux/lib/${CMAKE_BUILD_TYPE}/libACE-5.7.5.so" DESTINATION bin)
install(FILES "${CMAKE_SOURCE_DIR}/externals/linux/lib/${CMAKE_BUILD_TYPE}/libOnixS.IceImpactMulticastPriceFeedHandlerCpp.so.3.16.0.0" DESTINATION bin)
install(FILES "${CMAKE_SOURCE_DIR}/externals/src/emumba/sparkd.lic" DESTINATION bin)
endif()
-215
View File
@@ -1,215 +0,0 @@
{
"version": 4,
"cmakeMinimumRequired": {
"major": 3,
"minor": 23,
"patch": 0
},
"configurePresets": [
{
"name": "spark",
"condition": {
"type": "equals",
"lhs": "${hostSystemName}",
"rhs": "Windows"
},
"generator": "Visual Studio 17 2022",
"binaryDir": "${sourceDir}/build/${presetName}",
"environment": {
"SPARK_CMAKE_CXX_FLAGS": "/MP /WX /wd4250 /wd4251 /wd4244 /wd4267 /wd4355 /wd4275 /wd4345 /bigobj /EHsc /DCURL_STATICLIB /D_WINSOCK_DEPRECATED_NO_WARNINGS /D__TBB_NO_IMPLICIT_LINKAGE /DBOOST_ALL_NO_LIB /std:c++20 /D_SCL_SECURE_NO_WARNINGS /D_CRT_SECURE_NO_WARNINGS /D_WIN32_WINNT=0x0600"
},
"cacheVariables": {
"CMAKE_CXX_FLAGS": "$env{SPARK_CMAKE_CXX_FLAGS}",
"CMAKE_CXX_FLAGS_DEBUG": "$env{SPARK_CMAKE_CXX_FLAGS} /MTd",
"CMAKE_CXX_FLAGS_RELEASE": "$env{SPARK_CMAKE_CXX_FLAGS} /MT",
"CMAKE_CXX_STANDARD": "20",
"CMAKE_INSTALL_PREFIX": "${sourceDir}/install/${presetName}",
"CMAKE_SHARED_LINKER_FLAGS_DEBUG": "/DEBUG",
"CMAKE_SHARED_LINKER_FLAGS_RELEASE": "/OPT:REF /OPT:ICF /LTCG",
"CMAKE_TOOLCHAIN_FILE": "${sourceDir}/vcpkg/scripts/buildsystems/vcpkg.cmake",
"EXTERNALS_ROOT": "${sourceDir}/externals/windows",
"CONFIG_DEFAULTS_PATH": "config/defaults/*.conf",
"DOTNET_BINARY_DIR": "${sourceDir}/build/$<CONFIG>/bin/net7.0;${sourceDir}/build/$<CONFIG>/bin/net7.0-windows",
"EXPORT_MD_CONSUMER": {
"type": "BOOL",
"value": "ON"
}
}
},
{
"name": "sparkd",
"condition": {
"type": "equals",
"lhs": "${hostSystemName}",
"rhs": "Linux"
},
"hidden": true,
"generator": "Ninja",
"binaryDir": "${sourceDir}/build/${presetName}",
"cacheVariables": {
"platform": "",
"CMAKE_CXX_STANDARD": "20",
"CMAKE_INSTALL_PREFIX": "${sourceDir}/install/${presetName}",
"CMAKE_EXE_LINKER_FLAGS": "-Wno-undef",
"CONFIG_DEFAULTS_PATH": "config/defaults/*.conf",
"EXTERNALS_ROOT": "${sourceDir}/externals/linux",
"BUILD_SDK": {
"type": "BOOL",
"value": "OFF"
},
"BUILD_ADMIN_WEB_APP": {
"type": "BOOL",
"value": "ON"
}
}
},
{
"name": "sparkd-debug",
"inherits": "sparkd",
"hidden": true,
"cacheVariables": {
"CMAKE_BUILD_TYPE": "Debug",
"CMAKE_EXPORT_COMPILE_COMMANDS": {
"type": "BOOL",
"value": "ON"
},
"CCAPI_LOG_LEVEL": "Info"
}
},
{
"name": "sparkd-release",
"inherits": "sparkd",
"hidden": true,
"cacheVariables": {
"CMAKE_BUILD_TYPE": "Release",
"CCAPI_LOG_LEVEL": "Warn"
}
},
{
"name": "sparkd-debug-clang",
"inherits": "sparkd-debug",
"displayName": "Sparkd (Debug | Clang)",
"description": "Debug build compiled w/ clang",
"cacheVariables": {
"CMAKE_C_COMPILER": "clang",
"CMAKE_CXX_COMPILER": "clang++",
"CMAKE_CXX_FLAGS_DEBUG": "-g -fPIC -Wall -pedantic -Wextra -Werror -Wno-missing-braces -Wno-ignored-qualifiers --std=c++20 -fdiagnostics-color -DDEBUG"
}
},
{
"name": "sparkd-debug-gcc",
"inherits": "sparkd-debug",
"displayName": "Sparkd (Debug | Gcc)",
"description": "Debug build compiled w/ gcc",
"cacheVariables": {
"CMAKE_C_COMPILER": "gcc",
"CMAKE_CXX_COMPILER": "g++",
"CMAKE_CXX_FLAGS_DEBUG": "-g -fPIC -Wall -pedantic -Wextra -Werror -Wno-missing-braces -Wno-ignored-qualifiers --std=c++20 -fdiagnostics-color -Wno-stringop-overread -DDEBUG"
}
},
{
"name": "sparkd-release-clang",
"inherits": "sparkd-release",
"displayName": "Sparkd (Release | Clang)",
"description": "Release build compiled w/ clang",
"cacheVariables": {
"CMAKE_C_COMPILER": "clang",
"CMAKE_CXX_COMPILER": "clang++",
"CMAKE_CXX_FLAGS_RELEASE": "-fPIC -Wall -pedantic -Wextra -Werror -Wno-missing-braces -Wno-ignored-qualifiers --std=c++20 -fdiagnostics-color -fno-omit-frame-pointer -DNDEBUG -O3"
}
},
{
"name": "sparkd-release-gcc",
"inherits": "sparkd-release",
"displayName": "Sparkd (Release | Gcc)",
"description": "Release build compiled w/ gcc",
"cacheVariables": {
"CMAKE_C_COMPILER": "gcc",
"CMAKE_CXX_COMPILER": "g++",
"CMAKE_CXX_FLAGS_RELEASE": "-fPIC -Wall -pedantic -Wextra -Werror -Wno-missing-braces -Wno-ignored-qualifiers -Wno-stringop-overflow --std=c++20 -fdiagnostics-color -Wno-stringop-overread -Wno-maybe-uninitialized -fno-omit-frame-pointer -DNDEBUG -O3"
}
}
],
"buildPresets": [
{
"name": "spark",
"condition": {
"type": "equals",
"lhs": "${hostSystemName}",
"rhs": "Windows"
},
"hidden": true
},
{
"name": "spark-debug",
"displayName": "Spark (Debug)",
"inherits": "spark",
"configurePreset": "spark",
"configuration": "Debug"
},
{
"name": "spark-release",
"displayName": "Spark (Release)",
"inherits": "spark",
"configurePreset": "spark",
"configuration": "Release"
},
{
"name": "sparkd",
"condition": {
"type": "equals",
"lhs": "${hostSystemName}",
"rhs": "Linux"
},
"hidden": true
},
{
"name": "sparkd-debug-clang",
"configurePreset": "sparkd-debug-clang",
"displayName": "Sparkd (Debug | Clang)",
"inherits": "sparkd"
},
{
"name": "sparkd-debug-clang-j6",
"configurePreset": "sparkd-debug-clang",
"displayName": "Sparkd (Debug | Clang | jobs=6)",
"inherits": "sparkd",
"jobs": 6
},
{
"name": "sparkd-debug-gcc",
"configurePreset": "sparkd-debug-gcc",
"displayName": "Sparkd (Debug | Gcc)",
"inherits": "sparkd"
},
{
"name": "sparkd-release-clang",
"configurePreset": "sparkd-release-clang",
"displayName": "Sparkd (Release | Clang)",
"inherits": "sparkd"
},
{
"name": "sparkd-release-gcc",
"configurePreset": "sparkd-release-gcc",
"displayName": "Sparkd (Release | Gcc)",
"inherits": "sparkd"
}
]
}
-39
View File
@@ -1,39 +0,0 @@
include(${CMAKE_SOURCE_DIR}/cmake/PackBasic.cmake)
include(GNUInstallDirs)
function(install_basic)
set(_options)
set(_one_value_args)
set(_multi_value_args HEADERS)
cmake_parse_arguments(_ARGS "${_options}" "${_one_value_args}" "${_multi_value_args}" ${ARGN})
if (_ARGS_HEADERS)
set(${PROJECT_NAME}_HEADERS ${_ARGS_HEADERS})
else()
file(
GLOB_RECURSE ${PROJECT_NAME}_HEADERS
RELATIVE ${CMAKE_CURRENT_SOURCE_DIR}
*.h
)
endif()
target_sources(${PROJECT_NAME}
PUBLIC
FILE_SET HEADERS FILES ${${PROJECT_NAME}_HEADERS})
install(
TARGETS ${PROJECT_NAME}
EXPORT ${PROJECT_NAME}Targets
RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
FILE_SET HEADERS DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}
)
install(
EXPORT ${PROJECT_NAME}Targets
FILE ${PROJECT_NAME}Targets.cmake
NAMESPACE ${PROJECT_NAME}::
DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/${PROJECT_NAME})
pack_basic()
endfunction()
-36
View File
@@ -1,36 +0,0 @@
include(CMakePackageConfigHelpers)
function(pack_basic)
find_package(Git QUIET)
if(GIT_FOUND)
execute_process(
COMMAND ${GIT_EXECUTABLE} describe --tags --always --dirty
WORKING_DIRECTORY ${CMAKE_SOURCE_DIR}
OUTPUT_VARIABLE PROJECT_VERSION
OUTPUT_STRIP_TRAILING_WHITESPACE
)
endif()
if(NOT GIT_FOUND OR PROJECT_VERSION STREQUAL "")
set(PROJECT_VERSION "0.0.0")
endif()
write_basic_package_version_file(
"${CMAKE_CURRENT_BINARY_DIR}/${PROJECT_NAME}ConfigVersion.cmake"
VERSION ${PROJECT_VERSION}
COMPATIBILITY AnyNewerVersion
)
configure_package_config_file(
"${CMAKE_CURRENT_SOURCE_DIR}/Config.cmake.in"
"${CMAKE_CURRENT_BINARY_DIR}/${PROJECT_NAME}Config.cmake"
INSTALL_DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/${PROJECT_NAME}
)
install(
FILES
"${CMAKE_CURRENT_BINARY_DIR}/${PROJECT_NAME}Config.cmake"
"${CMAKE_CURRENT_BINARY_DIR}/${PROJECT_NAME}ConfigVersion.cmake"
DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/${PROJECT_NAME})
endfunction()
-12
View File
@@ -1,12 +0,0 @@
function(print_list var)
set(CMAKE_MESSAGE_INDENT "")
set(_var_str "")
foreach(item IN LISTS ${var})
set(_var_str "${_var_str}\n ${item}")
endforeach()
if ("${ARGN}" STREQUAL "VERBOSE")
message(VERBOSE "***${var}:${_var_str}")
else()
message("***${var}:${_var_str}")
endif()
endfunction()
+2 -2
View File
@@ -1,5 +1,5 @@
set(Protobuf_PROTOC_EXECUTABLE "${EXTERNALS_BIN}/protoc")
set(PROTOBUF_INCLUDE_DIRS "${EXTERNALS_INCLUDE}")
set(Protobuf_PROTOC_EXECUTABLE "${SPARK_BIN}/protoc")
set(PROTOBUF_INCLUDE_DIRS "${SPARK_INCLUDE}")
set(PROTOBUF_STATIC_LIB "libprotobuf")
function(Protobuf_Generate_Cpp SRCS HDRS)
Submodule
+1
Submodule docker/linux added at 6537812262.
+1
Submodule docker/windows added at de7d40c09d.
+15 -30
View File
@@ -1,9 +1,11 @@
Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio Version 17
VisualStudioVersion = 17.3.32922.545
# Visual Studio Version 16
VisualStudioVersion = 16.0.30114.105
MinimumVisualStudioVersion = 15.0.26124.0
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "spark_api", "src\client\spark_api\spark_api.csproj", "{DC9A8975-8211-4FC9-A9BA-C8B9D26AD481}"
EndProject
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "libspark", "build\src\lib\libspark.vcxproj", "{9FA60215-26AF-3EB7-AB89-D4F4B126EF40}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Spark", "src\client\spark\Spark.csproj", "{9A4D4D07-1AB6-4B2B-B111-A4F34D6C267E}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "sparkcmd", "src\client\sparkcmd\sparkcmd.csproj", "{387566C6-C6F6-412C-A30C-9855BBCB4816}"
@@ -11,13 +13,12 @@ EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "spark_core", "src\client\spark_core\spark_core.csproj", "{6E449EB6-20AC-4FA6-B8D9-10F4BB7E1FEE}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "spark_sdk", "src\client\spark_sdk\spark_sdk.csproj", "{6963C314-83C4-4667-B0D0-C2F7AE208C29}"
ProjectSection(ProjectDependencies) = postProject
{9FA60215-26AF-3EB7-AB89-D4F4B126EF40} = {9FA60215-26AF-3EB7-AB89-D4F4B126EF40}
EndProjectSection
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "spark_test", "src\client\spark_test\spark_test.csproj", "{ECD78CC5-138F-4809-A764-2358C2AC2E82}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "spark_websocket", "src\client\spark_websocket\spark_websocket.csproj", "{3201359D-C071-4089-9EDE-B04D759F1508}"
EndProject
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "spark_api_server", "src\client\spark_api_server\spark_api_server.csproj", "{2B8C5D01-FF78-4BFA-B332-5E430586DAF9}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|x64 = Debug|x64
@@ -34,14 +35,14 @@ Global
{DC9A8975-8211-4FC9-A9BA-C8B9D26AD481}.Release|x64.Build.0 = Release|x64
{DC9A8975-8211-4FC9-A9BA-C8B9D26AD481}.RelWithDebInfo|x64.ActiveCfg = Release|x64
{DC9A8975-8211-4FC9-A9BA-C8B9D26AD481}.RelWithDebInfo|x64.Build.0 = Release|x64
{FDC3A021-386E-3A2C-A7EB-CBE94A95BE25}.Debug|x64.ActiveCfg = Debug|x64
{FDC3A021-386E-3A2C-A7EB-CBE94A95BE25}.Debug|x64.Build.0 = Debug|x64
{FDC3A021-386E-3A2C-A7EB-CBE94A95BE25}.MinSizeRel|x64.ActiveCfg = MinSizeRel|x64
{FDC3A021-386E-3A2C-A7EB-CBE94A95BE25}.MinSizeRel|x64.Build.0 = MinSizeRel|x64
{FDC3A021-386E-3A2C-A7EB-CBE94A95BE25}.Release|x64.ActiveCfg = Release|x64
{FDC3A021-386E-3A2C-A7EB-CBE94A95BE25}.Release|x64.Build.0 = Release|x64
{FDC3A021-386E-3A2C-A7EB-CBE94A95BE25}.RelWithDebInfo|x64.ActiveCfg = RelWithDebInfo|x64
{FDC3A021-386E-3A2C-A7EB-CBE94A95BE25}.RelWithDebInfo|x64.Build.0 = RelWithDebInfo|x64
{9FA60215-26AF-3EB7-AB89-D4F4B126EF40}.Debug|x64.ActiveCfg = Debug|x64
{9FA60215-26AF-3EB7-AB89-D4F4B126EF40}.Debug|x64.Build.0 = Debug|x64
{9FA60215-26AF-3EB7-AB89-D4F4B126EF40}.MinSizeRel|x64.ActiveCfg = MinSizeRel|x64
{9FA60215-26AF-3EB7-AB89-D4F4B126EF40}.MinSizeRel|x64.Build.0 = MinSizeRel|x64
{9FA60215-26AF-3EB7-AB89-D4F4B126EF40}.Release|x64.ActiveCfg = Release|x64
{9FA60215-26AF-3EB7-AB89-D4F4B126EF40}.Release|x64.Build.0 = Release|x64
{9FA60215-26AF-3EB7-AB89-D4F4B126EF40}.RelWithDebInfo|x64.ActiveCfg = RelWithDebInfo|x64
{9FA60215-26AF-3EB7-AB89-D4F4B126EF40}.RelWithDebInfo|x64.Build.0 = RelWithDebInfo|x64
{9A4D4D07-1AB6-4B2B-B111-A4F34D6C267E}.Debug|x64.ActiveCfg = Debug|x64
{9A4D4D07-1AB6-4B2B-B111-A4F34D6C267E}.Debug|x64.Build.0 = Debug|x64
{9A4D4D07-1AB6-4B2B-B111-A4F34D6C267E}.MinSizeRel|x64.ActiveCfg = Release|x64
@@ -82,22 +83,6 @@ Global
{ECD78CC5-138F-4809-A764-2358C2AC2E82}.Release|x64.Build.0 = Release|x64
{ECD78CC5-138F-4809-A764-2358C2AC2E82}.RelWithDebInfo|x64.ActiveCfg = Release|x64
{ECD78CC5-138F-4809-A764-2358C2AC2E82}.RelWithDebInfo|x64.Build.0 = Release|x64
{3201359D-C071-4089-9EDE-B04D759F1508}.Debug|x64.ActiveCfg = Debug|x64
{3201359D-C071-4089-9EDE-B04D759F1508}.Debug|x64.Build.0 = Debug|x64
{3201359D-C071-4089-9EDE-B04D759F1508}.MinSizeRel|x64.ActiveCfg = Debug|x64
{3201359D-C071-4089-9EDE-B04D759F1508}.MinSizeRel|x64.Build.0 = Debug|x64
{3201359D-C071-4089-9EDE-B04D759F1508}.Release|x64.ActiveCfg = Release|x64
{3201359D-C071-4089-9EDE-B04D759F1508}.Release|x64.Build.0 = Release|x64
{3201359D-C071-4089-9EDE-B04D759F1508}.RelWithDebInfo|x64.ActiveCfg = Release|x64
{3201359D-C071-4089-9EDE-B04D759F1508}.RelWithDebInfo|x64.Build.0 = Release|x64
{2B8C5D01-FF78-4BFA-B332-5E430586DAF9}.Debug|x64.ActiveCfg = Debug|x64
{2B8C5D01-FF78-4BFA-B332-5E430586DAF9}.Debug|x64.Build.0 = Debug|x64
{2B8C5D01-FF78-4BFA-B332-5E430586DAF9}.MinSizeRel|x64.ActiveCfg = Debug|x64
{2B8C5D01-FF78-4BFA-B332-5E430586DAF9}.MinSizeRel|x64.Build.0 = Debug|x64
{2B8C5D01-FF78-4BFA-B332-5E430586DAF9}.Release|x64.ActiveCfg = Release|x64
{2B8C5D01-FF78-4BFA-B332-5E430586DAF9}.Release|x64.Build.0 = Release|x64
{2B8C5D01-FF78-4BFA-B332-5E430586DAF9}.RelWithDebInfo|x64.ActiveCfg = Release|x64
{2B8C5D01-FF78-4BFA-B332-5E430586DAF9}.RelWithDebInfo|x64.Build.0 = Release|x64
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
+53 -55
View File
@@ -1,55 +1,53 @@
<Project>
<PropertyGroup>
<ComputerSpecificConfig>..\..\tools\override\$(computername).props</ComputerSpecificConfig>
<SparkRoot>$([System.IO.Path]::GetFullPath($(MSBuildThisFileDirectory)\..\..))</SparkRoot>
<SourceRoot>$([System.IO.Path]::GetFullPath($(SparkRoot)\src))</SourceRoot>
<Externals>$(SparkRoot)\externals\windows</Externals>
<DepotName>$([System.IO.Path]::GetFileName($([System.IO.Path]::GetFullPath($(SparkRoot)))))</DepotName>
<ErrorReport>None</ErrorReport>
<Prefer32Bit>False</Prefer32Bit>
<Deterministic>true</Deterministic>
<EnableDefaultContentItems>False</EnableDefaultContentItems>
<ShowMissingItemTypes>false</ShowMissingItemTypes>
<Configuration Condition="'$(configuration)'==''">Debug</Configuration>
<EnablePreviewFeatures>true</EnablePreviewFeatures>
<LangVersion>11</LangVersion>
</PropertyGroup>
<PropertyGroup Label="Output">
<BaseOutputPath>$(SparkRoot)\build\$(Configuration)</BaseOutputPath>
<OutputPath>$(BaseOutputPath)\bin</OutputPath>
<BaseIntermediateOutputPath>$(BaseOutputPath)\obj\$(MSBuildProjectName)</BaseIntermediateOutputPath>
<IntermediateOutputPath>$(BaseOutputPath)\obj\$(MSBuildProjectName)</IntermediateOutputPath>
<ProtoOutputPath>$(BaseOutputPath)\obj\$(MSBuildProjectName)</ProtoOutputPath>
<GenDir>$(BaseOutputPath)\gen\$(MSBuildProjectName)</GenDir>
</PropertyGroup>
<Import
Project="$(ComputerSpecificConfig)"
Condition="Exists($(ComputerSpecificConfig))" />
<PropertyGroup Label="ProtoBuf">
<ProtocPluginBase>$(SparkRoot)\src\lib\api\service_compiler</ProtocPluginBase>
<protoc>$(Externals)\bin\protoc.exe</protoc>
<protogen>$(Externals)\bin\protogen.exe</protogen>
</PropertyGroup>
<ItemDefinitionGroup>
<Proto2></Proto2>
<Proto3>
<OutBase>$(IntermediateOutputPath)\gen\%(relativedir)</OutBase>
<OutCS>%(OutBase)%(FileName).cs</OutCS>
<OutCSClient>%(OutBase)%(FileName).client.pb.cs</OutCSClient>
<OutCSServer>%(OutBase)%(FileName).server.pb.cs</OutCSServer>
<OutCSImmutable>%(OutBase)%(FileName).immutable.pb.cs</OutCSImmutable>
<CompileOptions></CompileOptions>
</Proto3>
<Proto3Excel>
<OutBase>$(IntermediateOutputPath)\gen\%(relativedir)</OutBase>
<OutCSExcel>%(OutBase)%(FileName).excel.pb.cs</OutCSExcel>
<CompileOptions></CompileOptions>
</Proto3Excel>
</ItemDefinitionGroup>
</Project>
<Project>
<PropertyGroup>
<ComputerSpecificConfig>..\..\tools\override\$(computername).props</ComputerSpecificConfig>
<SparkRoot>$([System.IO.Path]::GetFullPath($(MSBuildThisFileDirectory)\..\..))</SparkRoot>
<SourceRoot>$([System.IO.Path]::GetFullPath($(SparkRoot)\src))</SourceRoot>
<Externals>$(SparkRoot)\externals\windows</Externals>
<DepotName>$([System.IO.Path]::GetFileName($([System.IO.Path]::GetFullPath($(SparkRoot)))))</DepotName>
<ErrorReport>None</ErrorReport>
<Prefer32Bit>False</Prefer32Bit>
<Deterministic>true</Deterministic>
<EnableDefaultContentItems>False</EnableDefaultContentItems>
<ShowMissingItemTypes>false</ShowMissingItemTypes>
<Configuration Condition="'$(configuration)'==''">Debug</Configuration>
<EnablePreviewFeatures>true</EnablePreviewFeatures>
</PropertyGroup>
<PropertyGroup Label="Output">
<BaseOutputPath>$(SparkRoot)\build\$(Configuration)</BaseOutputPath>
<OutputPath>$(BaseOutputPath)\bin</OutputPath>
<BaseIntermediateOutputPath>$(BaseOutputPath)\obj\$(MSBuildProjectName)</BaseIntermediateOutputPath>
<IntermediateOutputPath>$(BaseOutputPath)\obj\$(MSBuildProjectName)</IntermediateOutputPath>
<GenDir>$(BaseOutputPath)\gen\$(MSBuildProjectName)</GenDir>
</PropertyGroup>
<Import
Project="$(ComputerSpecificConfig)"
Condition="Exists($(ComputerSpecificConfig))" />
<PropertyGroup Label="ProtoBuf">
<ProtocPluginBase>$(SparkRoot)\src\lib\api\service_compiler</ProtocPluginBase>
<protoc>$(Externals)\bin\protoc.exe</protoc>
<protogen>$(Externals)\bin\protogen.exe</protogen>
</PropertyGroup>
<ItemDefinitionGroup>
<Proto2></Proto2>
<Proto3>
<OutBase>$(IntermediateOutputPath)\gen\%(relativedir)</OutBase>
<OutCS>%(OutBase)%(FileName).cs</OutCS>
<OutCSClient>%(OutBase)%(FileName).client.pb.cs</OutCSClient>
<OutCSServer>%(OutBase)%(FileName).server.pb.cs</OutCSServer>
<OutCSImmutable>%(OutBase)%(FileName).immutable.pb.cs</OutCSImmutable>
<CompileOptions></CompileOptions>
</Proto3>
<Proto3Excel>
<OutBase>$(IntermediateOutputPath)\gen\%(relativedir)</OutBase>
<OutCSExcel>%(OutBase)%(FileName).excel.pb.cs</OutCSExcel>
<CompileOptions></CompileOptions>
</Proto3Excel>
</ItemDefinitionGroup>
</Project>
@@ -43,7 +43,6 @@ namespace mbts.spark {
readonly ObservableHashSet<AnalyticsExpirationParametersRowVM> _selected_rows = new();
readonly DeferrableAction _raise_selected_rows_changed;
readonly IRaiseCanExecuteChangedCommand _set_driver_to_nearest_exp_cmd;
IList<string>? _pending_selected_symbols;
AnalyticsExpirationParametersMap? _parameter_map;
(ICommand cmd, IDisposable can_exe_sub)? _smart_copy_roll_target_to_selection_cmd;
@@ -66,7 +65,9 @@ namespace mbts.spark {
_is_dirty = backing(nameof(is_dirty), () => rows.Any(r => r.is_dirty));
if (startup_data is not null) {
_pending_selected_symbols = startup_data.selected_symbols;
if (!startup_data.selected_symbols.is_null_or_empty()) {
selected_symbols.AddRange(startup_data.selected_symbols);
}
auto_copy_rolls_is_checked = startup_data.auto_copy_rolls_is_checked;
auto_copy_rates_is_checked = startup_data.auto_copy_rates_is_checked;
}
@@ -296,8 +297,8 @@ namespace mbts.spark {
symbols.sync_with(_parameters.Select(p => p.security.symbol).Distinct().Ordered());
using var _ = _sync_visible_rows.defer();
if (is_first_update) {
selected_symbols.sync_with(_pending_selected_symbols?.Intersect(symbols) ?? symbols);
_pending_selected_symbols = null;
// select all symbols on first update
selected_symbols.sync_with(symbols);
}
}
@@ -96,7 +96,7 @@ namespace mbts.spark {
get => _core_settings.font_weight_override;
set {
using var _ = detect_property_change();
_core_settings.with(font_weight_override: value.HasValue ? new(value) : null);
_core_settings.with(font_weight_override: value.HasValue ? new NullableFontWeightProto(value) : null);
}
}
@@ -145,7 +145,7 @@ namespace mbts {
!(x == y);
public override string ToString() =>
$"{security_tuple} {SecurityFormatter.format_expiration(expiration)}";
$"{security_tuple} {expiration.ToShortDateString()}";
}
[ProtoContract]
@@ -3,16 +3,15 @@
using mbts.co2;
namespace mbts.analytics {
using Size = System.Single;
public class VolSurfaceMDUnit : IEquatable<VolSurfaceMDUnit> {
public readonly double bid_price, ask_price;
public readonly Size bid_size, ask_size;
public readonly uint bid_size, ask_size;
public readonly double mark_price = double.NaN;
private static VolSurfaceMDUnit _empty =
new VolSurfaceMDUnit(Double.NaN, 0, Double.NaN, 0, Double.NaN);
public VolSurfaceMDUnit(double this_bid_price, Size this_bid_size,
double this_ask_price, Size this_ask_size,
public VolSurfaceMDUnit(double this_bid_price, uint this_bid_size,
double this_ask_price, uint this_ask_size,
double this_mark_price) {
bid_price = this_bid_price;
bid_size = this_bid_size;
@@ -29,7 +28,7 @@ namespace mbts.analytics {
public VolSurfaceMDUnit(NativePriceSize bid, NativePriceSize ask,
double mark_price)
: this(bid.price, bid.size_f, ask.price, ask.size_f, mark_price) {
: this(bid.price, bid.size, ask.price, ask.size, mark_price) {
}
public bool is_two_sided() { return bid_size != 0 && ask_size != 0; }
@@ -42,7 +41,7 @@ namespace mbts.analytics {
}
public double get_weighted_mid_price(bool get_one_sided_mid = true) {
Size sum_q = bid_size + ask_size;
uint sum_q = bid_size + ask_size;
if (sum_q == 0) {
return Double.NaN;
}
+1 -7
View File
@@ -52,16 +52,10 @@ namespace bts {
string rv = "MergedMDDaemon Options:\n";
foreach (var kv in sec_map) {
var sec = kv.Value.security;
var md = kv.Value.md;
ulong time = 0;
NativePriceSize bid, ask;
var has_md = md.get_bbo(ref time, out bid, out ask);
if (sec.HasOption) {
rv += $"id: {kv.Key} desc: {sec.security_desc()} sym: {sec.Symbol} " +
$"exp: {sec.security_expiration()} " +
$"k: {sec.Option.Strike} cp: {sec.Option.CallPut} " +
$"bid: p: {bid.price} q: {bid.size} qf: {bid.size_f} ask: p: {ask.price} q: {ask.size} qf: {ask.size_f}" +
"\n";
$"k: {sec.Option.Strike} cp: {sec.Option.CallPut}" + "\n";
}
}
Log.Gen.info(rv);
@@ -31,7 +31,7 @@
_window_factories = new() {
new MarketViewWindowFactory(
this, bus, settings_hub, orders_model, position_model, sec_meta_store),
new OptionsViewWindowFactory(this, orders_model, bus),
new OptionsViewWindowFactory(this, bus),
new TimeAndSalesWindowFactory(this, bus, consumer, settings_hub, orders_model.security_auxiliary_model),
};
@@ -79,12 +79,10 @@ namespace bts.shell.market_view {
var ask_col_index = columns.FindIndex(x => x.id == MarketViewWindowFactory.col_id(Columns.Ask));
if (bid_col_index > -1 && ask_col_index > -1) {
if (!columns[bid_col_index].background_color_override.HasValue) {
columns[bid_col_index] = columns[bid_col_index].with(
background_color_override: new(BTSColors.MarketData.bid));
columns[bid_col_index] = columns[bid_col_index].with(background_color_override: new NullableColorProto(BTSColors.MarketData.bid.value));
}
if (!columns[ask_col_index].background_color_override.HasValue) {
columns[ask_col_index] = columns[ask_col_index].with(
background_color_override: new(BTSColors.MarketData.ask));
columns[ask_col_index] = columns[ask_col_index].with(background_color_override: new NullableColorProto(BTSColors.MarketData.ask.value));
}
}
// and enable background color upgrade
@@ -70,13 +70,11 @@ namespace bts.shell {
bool applied = false;
if (bid_col_index > -1 && ask_col_index > -1) {
if (!columns[bid_col_index].background_color_override.HasValue) {
columns[bid_col_index] = columns[bid_col_index].with(
background_color_override: new(BTSColors.MarketData.bid));
columns[bid_col_index] = columns[bid_col_index].with(background_color_override: new NullableColorProto(BTSColors.MarketData.bid.value));
applied = true;
}
if (!columns[ask_col_index].background_color_override.HasValue) {
columns[ask_col_index] = columns[ask_col_index].with(
background_color_override: new(BTSColors.MarketData.ask));
columns[ask_col_index] = columns[ask_col_index].with(background_color_override: new NullableColorProto(BTSColors.MarketData.ask.value));
applied = true;
}
}
@@ -10,14 +10,12 @@ namespace mbts.spark {
class OptionsViewWindowFactory : ShellWindowFactory<OptionsViewSettings> {
readonly IBus _bus;
readonly NMSheetAllTaskingDataSource _tasking_datasource;
public OptionsViewWindowFactory(IShellModule module, OrdersModel orders_model, IBus bus)
public OptionsViewWindowFactory(IShellModule module, IBus bus)
: base(module, OptionsViewWindow.WINDOW_TYPE) {
_bus = bus;
_dispose = bus.subscribe(SparkTags.show_default_options_view).OnDispatcher().Subscribe(
sc => _bus.post(SparkTags.ShowWindow, _create(OptionsViewSettings.Default(sc))));
_tasking_datasource = new NMSheetAllTaskingDataSource(orders_model, bus);
}
public override Task<IShellWindow> load(OptionsViewSettings state) =>
@@ -410,13 +410,13 @@ namespace mbts.spark {
day_change = new DaySettings {
// (neutral)
font = _default_font,
background_color = Colors.Transparent.to_uint(),
background_color = Colors.Transparent.rgb_color(),
// negative
negative_font_color = Colors.White.to_uint(),
negative_background_color = Colors.Red.to_uint(),
negative_font_color = Colors.White.rgb_color(),
negative_background_color = Colors.Red.rgb_color(),
// positive
positive_font_color = Colors.White.to_uint(),
positive_background_color = Colors.Green.to_uint()
positive_font_color = Colors.White.rgb_color(),
positive_background_color = Colors.Green.rgb_color()
},
session_low = _default_item,
session_high = _default_item,
@@ -431,8 +431,8 @@ namespace mbts.spark {
public static LadderPanelPricePointSettings tt_default {
get {
var rv = historic_default;
rv.day_change.background_color = Color.FromRgb(113, 201, 69).to_uint();
rv.day_change.font.font_color = Colors.Black.to_uint();
rv.day_change.background_color = Color.FromRgb(113, 201, 69).rgb_color();
rv.day_change.font.font_color = Colors.Black.rgb_color();
return rv;
}
}
@@ -484,7 +484,7 @@ namespace mbts.spark {
static ItemSettings _default_item =>
new ItemSettings {
font = _default_font,
background_color = Colors.Transparent.to_uint()
background_color = Colors.Transparent.rgb_color()
};
[ProtoContract]
@@ -97,7 +97,7 @@ namespace mbts.spark {
security_key = use_self_security ? null : selected_security_key,
price_type = _selected_price_type,
display = new LadderMarketBreakLine {
color = color.to_uint(),
color = color.rgb_color(),
show = show,
refresh_mode = refresh_mode
}
@@ -27,7 +27,7 @@ namespace mbts.spark {
class LadderOrderVM : DisposableViewModelBase {
static readonly Color _colorbg = Colors.White;
static readonly Color _darkbg = Color.FromRgb(0xbf, 0xbf, 0xbf);
static readonly Brush _color_bg_brush = _colorbg.to_uint().rgb_brush();
static readonly Brush _color_bg_brush = _colorbg.rgb_color().rgb_brush();
readonly LadderVM _owner;
readonly double _real_price;
@@ -218,21 +218,17 @@ namespace mbts.spark {
background = buy_sell_background_fill_color;
hoverbackground = _mk_hover_bg_brush(dark, _darkbg, 0);
_num_root_orders = 0;
_filled = 0;
_quantity = 0;
foreach (var n in _root_nodes) {
_num_root_orders++;
_filled += n.filled_quantity();
_quantity += n.quantity();
}
(_num_root_orders, _filled, _quantity) = _root_nodes
.Select(n => (1u, n.filled_quantity(), n.quantity()))
.Sum();
if (_num_root_orders == 1) {
var order = _root_nodes.First();
border = _owner.model.order_gateway.factory.get_metadata(order).Color.rgb_brush();
if (_orders.TryGetValue(order.Key, out var opm)) {
algo_studio_abbreviation = (opm.meta?.abbreviation).is_null_or_empty() ?
_abbreviate_algo(opm.algo) : opm.meta?.abbreviation ?? string.Empty;
border = opm.meta?.badge_color?.to_uint().rgb_brush() ?? border;
border = opm.meta?.badge_color?.rgb_color().rgb_brush() ?? border;
}
algo_type = order.order_type().is_bts_algo_type() ?
order.order_type() : CustomOrderDefinition.CustomOneofCase.None;
@@ -42,13 +42,13 @@ namespace mbts.spark {
public LadderPanelPricePointSettings.ItemSettings create() =>
new LadderPanelPricePointSettings.ItemSettings {
font = new FontParamsProto {
font_color = font_color.to_uint(),
font_color = font_color.rgb_color(),
font_size = font_size,
typeface = new(
font_family.name() ?? TextUtils.StandardFontFamilyName,
font_weight.ToOpenTypeWeight())
},
background_color = background_color.to_uint(),
background_color = background_color.rgb_color(),
show_label = show_label
};
@@ -111,11 +111,11 @@ namespace mbts.spark {
show_label = base_settings.show_label,
background_color = base_settings.background_color,
// negative
negative_font_color = negative_font_color.to_uint(),
negative_background_color = negative_background_color.to_uint(),
negative_font_color = negative_font_color.rgb_color(),
negative_background_color = negative_background_color.rgb_color(),
// positive
positive_font_color = positive_font_color.to_uint(),
positive_background_color = positive_background_color.to_uint()
positive_font_color = positive_font_color.rgb_color(),
positive_background_color = positive_background_color.rgb_color()
};
}
}
@@ -700,8 +700,8 @@ namespace mbts.spark {
font_weight = font_weight.ToOpenTypeWeight(),
width = width,
show = show,
foreground = foreground.to_uint(),
background = background.to_uint()
foreground = foreground.rgb_color(),
background = background.rgb_color()
};
}
}
@@ -891,7 +891,7 @@ namespace mbts.spark {
};
root_bd.SetBinding(
Border.BackgroundProperty, new Binding(nameof(background_brush)) { Source = this });
return root_bd;
return button;
}
}
@@ -231,7 +231,7 @@ namespace bts.shell {
sorting_criteria,
_vm.anchors,
filters,
state.grid.with(columns: cols, background: _vm.grid_background_color.to_uint()),
state.grid.with(columns: cols, background: _vm.grid_background_color.rgb_color()),
calc_type,
_vm.header_row_display,
menu_display: _menu_display_vm?.create());
@@ -68,10 +68,10 @@ namespace bts.shell.pnl {
typeface = new TypefaceProto(
cell_appearance.font_family?.name(),
(cell_appearance.font_weight ?? FontWeights.Normal).ToOpenTypeWeight()),
font_color = cell_appearance.foreground?.to_uint() ?? 0,
font_color = cell_appearance.foreground?.rgb_color() ?? 0,
font_size = cell_appearance.font_size,
},
background = cell_appearance.background?.to_uint()
background = cell_appearance.background?.rgb_color()
};
public PNLCellAppearance to_appearance() {
File diff suppressed because it is too large. Load diff
@@ -103,14 +103,14 @@ namespace bts.shell.pnl {
public PNLAnimation to_animation(PNLView.Columns key) =>
new PNLAnimation {
column = key,
foreground = is_font_color_overridden ? font_color_override.color.to_uint() : (uint?)null,
background = is_background_overridden ? background_override.color.to_uint() : (uint?)null,
foreground = is_font_color_overridden ? font_color_override.color.rgb_color() : (uint?)null,
background = is_background_overridden ? background_override.color.rgb_color() : (uint?)null,
font_weight = is_font_weight_overridden ? font_weight_override.ToOpenTypeWeight() : (int?)null
};
public PNLCellAppearanceProto to_appearance_proto() =>
new PNLCellAppearanceProto {
background = is_background_overridden ? background_override.color.to_uint() : (uint?)null,
background = is_background_overridden ? background_override.color.rgb_color() : (uint?)null,
font_params = to_font_params()
};
@@ -119,7 +119,7 @@ namespace bts.shell.pnl {
typeface = new TypefaceProto(
font_family_override?.name(),
is_font_weight_overridden ? font_weight_override.ToOpenTypeWeight() : 0),
font_color = is_font_color_overridden ? font_color_override.color.to_uint() : 0,
font_color = is_font_color_overridden ? font_color_override.color.rgb_color() : 0,
font_size = font_size_override
};
}
@@ -132,7 +132,7 @@ namespace bts.shell.pnl {
// group
var (group_cell_appearance, group_row_background_colors) = group_row_defaults.create();
s.group_cell_appearance = PNLCellAppearanceProto.from_appearance(group_cell_appearance);
s.group_background_colors.SetItems(group_row_background_colors.Select(c => c.to_uint()));
s.group_background_colors.SetItems(group_row_background_colors.Select(c => c.rgb_color()));
//
return s;
}
@@ -329,19 +329,20 @@ namespace bts.shell.pnl {
}
static (string desc, Color fg) _fills_title(Columns key) {
const uint net_fg = 0x333333u;
switch (key) {
case Columns.SODLongPos: return ("Open Buy Fills", BTSColors.MarketData.bid);
case Columns.SODShortPos: return ("Open Sell Fills", BTSColors.MarketData.ask);
case Columns.SODNetPos: return ("Open Fills", BTSColors.UI.default_text);
case Columns.SODNetPos: return ("Open Fills", net_fg.rgb_color());
case Columns.DayLongPos: return ("Day Buy Fills", BTSColors.MarketData.bid);
case Columns.DayShortPos: return ("Day Sell Fills", BTSColors.MarketData.ask);
case Columns.DayNetPos: return ("Day Fills", BTSColors.UI.default_text);
case Columns.DayNetPos: return ("Day Fills", net_fg.rgb_color());
case Columns.RawDayLongPos: return ("Raw Day Buy Fills", BTSColors.MarketData.bid);
case Columns.RawDayShortPos: return ("Raw Day Sell Fills", BTSColors.MarketData.ask);
case Columns.RawDayNetPos: return ("Raw Day Fills", BTSColors.UI.default_text);
case Columns.RawDayNetPos: return ("Raw Day Fills", net_fg.rgb_color());
case Columns.TotalLongPos: return ("All Buy Fills", BTSColors.MarketData.bid);
case Columns.TotalShortPos: return ("All Sell Fills", BTSColors.MarketData.ask);
case Columns.TotalNetPos: return ("All Fills", BTSColors.UI.default_text);
case Columns.TotalNetPos: return ("All Fills", net_fg.rgb_color());
default: throw ExceptionBuilder.Argument.unexpected_case(key, nameof(key));
}
}
@@ -367,7 +368,7 @@ namespace bts.shell.pnl {
switch (key) {
case Columns.WorkingLongPos: return ("Working Buy Orders", BTSColors.MarketData.bid);
case Columns.WorkingShortPos: return ("Working Sell Orders", BTSColors.MarketData.ask);
case Columns.WorkingNetPos: return ("Working Orders", BTSColors.UI.default_text);
case Columns.WorkingNetPos: return ("Working Orders", 0x333333u.rgb_color());
default: throw ExceptionBuilder.Argument.unexpected_case(key, nameof(key));
}
}
@@ -1,24 +0,0 @@
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using BCG;
namespace mbts.ui {
public class NMSheetAllTaskingData {
public IDictionary<UInt32, NMSheetTaskEyeData>
bids = new Dictionary<UInt32, NMSheetTaskEyeData>(),
asks = new Dictionary<UInt32, NMSheetTaskEyeData>();
public void add_sec(UInt32 sec, bts.api.Side side, double edge, double size) {
IDictionary<UInt32, NMSheetTaskEyeData> map = side == bts.api.Side.Buy ? bids : asks;
NMSheetTaskEyeData sec_data;
if (!map.TryGetValue(sec, out sec_data)) {
sec_data = new NMSheetTaskEyeData(true, edge, size);
map.Add(sec, sec_data);
}
}
}
}
@@ -1,6 +1,4 @@
using mbts.ui;
using System;
using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
@@ -19,7 +17,7 @@ namespace BCG
private readonly IDictionary<NMSheetSymbol, NMSheetSingleOptionData> _sym_data_map;
private readonly IDictionary<NMSheetSymbol, IDictionary<uint, BBOPacket>> _bbo_map;
private readonly IDictionary<uint, NMSheetTickerData> _complete_ticker_data;
private readonly NMSheetAllTaskingData _task_data;
private readonly TaskingConsolidatedData _task_data;
private readonly double[] _cached_sorted_strikes;
private readonly NMSheetExpiration[] _cached_sorted_expirations;
@@ -29,7 +27,7 @@ namespace BCG
public NMSheetData(IDictionary<NMSheetSymbol, NMSheetSingleOptionData> sym_data_map,
IDictionary<NMSheetSymbol, IDictionary<uint, BBOPacket>> bbo_map,
IDictionary<uint, NMSheetTickerData> complete_ticker_data,
NMSheetAllTaskingData task_data)
TaskingConsolidatedData task_data)
{
_sym_data_map = sym_data_map;
_bbo_map = bbo_map;
@@ -63,14 +61,14 @@ namespace BCG
public NMSheetData filter_for_strikes_in_tasks(bool is_on_only = false)
{
// if (_task_data != null)
// {
// IEnumerable<uint> eye_secs = _task_data.get_set_securities(mbts.tasks.TaskType.Eye, is_on_only),
// quoter_secs = _task_data.get_set_securities(mbts.tasks.TaskType.Quoter, is_on_only);
// HashSet<uint> all_secs = new HashSet<uint>(Enumerable.Concat(eye_secs, quoter_secs));
// return filter_data(this, all_secs);
// }
// else
if (_task_data != null)
{
IEnumerable<uint> eye_secs = _task_data.get_set_securities(mbts.tasks.TaskType.Eye, is_on_only),
quoter_secs = _task_data.get_set_securities(mbts.tasks.TaskType.Quoter, is_on_only);
HashSet<uint> all_secs = new HashSet<uint>(Enumerable.Concat(eye_secs, quoter_secs));
return filter_data(this, all_secs);
}
else
return this;
}
@@ -106,7 +104,9 @@ namespace BCG
return symbol_data.get_security_key(exp.option_expiration, strike, is_call, out security_key);
else
return false;
}
}
public TaskingConsolidatedData get_task_data() { return _task_data; }
#region INMSheetGridFacingData
@@ -31,8 +31,8 @@ namespace BCG {
private readonly IDictionary<DateTime, Tuple<double, double>> _option_exp_driver_detailed_price_data = new Dictionary<DateTime, Tuple<double, double>>();
private IDictionary<uint, BBOPacket> _bbo_data_map = new Dictionary<uint, BBOPacket>();
private IDictionary<uint, NMSheetTickerData> _ticker_data = new Dictionary<uint, NMSheetTickerData>();
private TaskingConsolidatedData _tasking_data;
private readonly ExchangeSecurityMap _sec_map;
private NMSheetAllTaskingData _ee_tasking_data = new NMSheetAllTaskingData();
public NMSheetSingleOptionData(NMSheetSymbol option,
NMSheetDataRequest data_request,
@@ -93,7 +93,7 @@ namespace BCG {
public void set_ticker(IDictionary<uint, NMSheetTickerData> ticker_data) { _ticker_data = ticker_data; }
public void set_task_data(NMSheetAllTaskingData tasking_data) { _ee_tasking_data = tasking_data; }
public void set_task_data(TaskingConsolidatedData tasking_data) { _tasking_data = tasking_data; }
/// Strikes are not sorted
public double[] get_strikes() { return _theo_data_map.get_strikes(); }
@@ -128,7 +128,7 @@ namespace BCG {
_fill_roll_over_data(cp_row, v, expiration, strike);
_fill_presave_theos(cp_row, v, expiration, strike);
NMSheetCallPutBidAskWrapper<NMSheetTaskEyeData> eye_data;
_fill_eye_data(tp_with_seckey, ref cp_row, out eye_data);
_fill_eye_data(tp_with_seckey, driver_bid_ask, call_bbo_packet, put_bbo_packet, ref cp_row, out eye_data);
NMSheetCallPutBidAskWrapper<NMSheetTaskQuoterData> quoter_data;
_fill_quoter_data(tp_with_seckey, driver_bid_ask, cp_row, out quoter_data);
NMSheetTickerData c_trade_data, p_ticker_data;
@@ -3,32 +3,45 @@
using bts.api;
using mbts.spark;
using mbts.ui;
namespace BCG {
public partial class NMSheetSingleOptionData {
// Gets the data from the bus, and fills in out_eye_data, and cp_row
private void _fill_eye_data(Triplet<mbts.spark.TheoPoint, uint, uint> tp_with_seckeys,
ref double[] cp_row,
out NMSheetCallPutBidAskWrapper<NMSheetTaskEyeData> out_eye_data) {
private void _fill_eye_data(Triplet<mbts.spark.TheoPoint, uint, uint> tp_with_seckeys, Tuple<double, double> driver_bid_ask, BBOPacket call_bbo, BBOPacket put_bbo,
ref double[] cp_row, out NMSheetCallPutBidAskWrapper<NMSheetTaskEyeData> out_eye_data) {
NMSheetTaskEyeData call_bid_data, call_ask_data, put_bid_data, put_ask_data;
// call
_get_eye_security_side_data(tp_with_seckeys.second, Side.Buy, out call_bid_data);
_get_eye_security_side_data(tp_with_seckeys.second, Side.Sell, out call_ask_data);
// put
_get_eye_security_side_data(tp_with_seckeys.third, Side.Buy, out put_bid_data);
_get_eye_security_side_data(tp_with_seckeys.third, Side.Sell, out put_ask_data);
out_eye_data = new NMSheetCallPutBidAskWrapper<NMSheetTaskEyeData>(
call_bid_data, call_ask_data, put_bid_data, put_ask_data);
_get_eye_security_side_data(tp_with_seckeys.first, PutOrCall.Call, Side.Buy, tp_with_seckeys.second, driver_bid_ask, call_bbo, out call_bid_data, ref cp_row,
NMSheetColumnName.call_ee_set_bid_edge, NMSheetColumnName.call_ee_set_bid_size, NMSheetColumnName.call_ee_bid_price);
_get_eye_security_side_data(tp_with_seckeys.first, PutOrCall.Call, Side.Sell, tp_with_seckeys.second, driver_bid_ask, call_bbo, out call_ask_data, ref cp_row,
NMSheetColumnName.call_ee_set_ask_edge, NMSheetColumnName.call_ee_set_ask_size, NMSheetColumnName.call_ee_ask_price);
_get_eye_security_side_data(tp_with_seckeys.first, PutOrCall.Put, Side.Buy, tp_with_seckeys.third, driver_bid_ask, put_bbo, out put_bid_data, ref cp_row,
NMSheetColumnName.put_ee_set_bid_edge, NMSheetColumnName.put_ee_set_bid_size, NMSheetColumnName.put_ee_bid_price);
_get_eye_security_side_data(tp_with_seckeys.first, PutOrCall.Put, Side.Sell, tp_with_seckeys.third, driver_bid_ask, put_bbo, out put_ask_data, ref cp_row,
NMSheetColumnName.put_ee_set_ask_edge, NMSheetColumnName.put_ee_set_ask_size, NMSheetColumnName.put_ee_ask_price);
out_eye_data = new NMSheetCallPutBidAskWrapper<NMSheetTaskEyeData>(call_bid_data, call_ask_data, put_bid_data, put_ask_data);
}
private void _get_eye_security_side_data(uint sec_key, Side side,
out NMSheetTaskEyeData inp_out_data) {
inp_out_data = null;
if (_ee_tasking_data == null)
return;
var map = side == Side.Buy ? _ee_tasking_data.bids : _ee_tasking_data.asks;
map.TryGetValue(sec_key, out inp_out_data);
private void _get_eye_security_side_data(mbts.spark.TheoPoint tp, PutOrCall cp, Side side, uint sec_key, Tuple<double, double> driver_bid_ask, BBOPacket bbo,
out NMSheetTaskEyeData inp_out_data,
ref double[] out_array,
NMSheetColumnName inp_edge_col, NMSheetColumnName inp_size_col, NMSheetColumnName eye_price_col) {
mbts.tasks.TaskSecurityEyeData eye_data = _tasking_data.get_eye_data(sec_key, side);
double edge = Double.NaN, eye_price = Double.NaN;
uint size = 0;
if (eye_data != null) {
edge = eye_data.edge;
size = eye_data.size;
/// Why is the eye sending the price instead of theo ?
if (eye_data.is_on)
eye_price = eye_data.eye_published_price;
else {
double theo = _compute_theo(tp, cp, side, driver_bid_ask);
eye_price = Math.Max(0.0, side == Side.Buy ? theo - edge : theo + edge);
}
}
out_array[(int)inp_edge_col] = edge;
out_array[(int)inp_size_col] = (double)size;
out_array[(int)eye_price_col] = eye_price;
inp_out_data = new NMSheetTaskEyeData(eye_data, side == Side.Buy ? eye_price >= BBOPacket.get_ask_price(bbo) : eye_price <= BBOPacket.get_bid_price(bbo));
}
}
}
@@ -1,88 +0,0 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using bts.api;
using mbts;
using mbts.spark;
using BCG;
using System.Collections;
using mbts.analytics;
using bts.api.analytics;
using System.Reactive.Linq;
using bts.api.orderman;
namespace mbts.ui {
internal class NMSheetAllTaskingDataSource {
private IBus _bus;
HighPerformanceTimer _timer = new HighPerformanceTimer();
private Nullable<DynamicOrderDefinitionImmutable> get_tasking_order(
OrderDefinitionImmutable def) {
if (def.HasCustomDef && def.CustomDef.HasComposite &&
def.CustomDef.Composite.HasDefinition &&
def.CustomDef.Composite.Definition.HasDynamic) {
var dyn = def.CustomDef.Composite.Definition.Dynamic;
if ("Tasking Eye".Equals(dyn.DynamicOrderType)) {
return dyn;
}
}
return null;
}
private bool is_working(OrderStatus status) {
return status == OrderStatus.Working ||
status == OrderStatus.PendingWorking ||
status == OrderStatus.Disconnected;
}
private void add_task_secs(ref NMSheetAllTaskingData t_data,
bts.api.Side side,
DynamicOrderDefinitionImmutable t_order) {
DynamicOrderParam sec_p;
if (t_order.OrderParams.TryGetValue("Securities", out sec_p)) {
if (!String.IsNullOrEmpty(sec_p.AsString)) {
DynamicOrderParam edge_param = null;
t_order.OrderParams.TryGetValue("Edge", out edge_param);
DynamicOrderParam size_param = null;
t_order.OrderParams.TryGetValue("Shot Size", out size_param);
if (edge_param != null && size_param != null) {
var toks = sec_p.AsString.Split(',');
foreach (var s in toks) {
UInt32 sec_key;
if (UInt32.TryParse(s.Trim(), out sec_key)) {
t_data.add_sec(sec_key, side, edge_param.AsDouble, size_param.AsDouble);
}
}
}
}
}
}
public NMSheetAllTaskingDataSource(OrdersModel orders_model, IBus bus) {
bts.Log.Gen.info("NMSheetAllTaskingDataSource constructed");
_bus = bus;
orders_model.on_orders.Subscribe(ords => {
_timer.start();
NMSheetAllTaskingData t_data = new NMSheetAllTaskingData();
bts.Log.Gen.info($"NMSheetAllTaskingDataSource on_orders n_orders: {ords.state.Values.Count()}");
foreach (var k in ords.state.Values) {
OrderRecordImmutable order = k.order;
if (!is_working(order.State.Status))
continue;
var t_dyn = get_tasking_order(order.Def);
if (t_dyn.HasValue) {
add_task_secs(ref t_data, order.Def.Side, t_dyn.Value);
}
}
_timer.stop();
bts.Log.Gen.info($"NMSheetAllTaskingDataSource n_bids: {t_data.bids.Count()} " +
$"n_asks: {t_data.asks.Count()} t_msecs: {_timer.lastIntervalTime}");
bus.post(SparkTags.TC2Tags.TaskData, t_data);
});
}
}
}
@@ -95,13 +95,12 @@ namespace BCG {
}
public class NMSheetTaskEyeData {
public readonly bool is_on;
public readonly double edge, size;
public readonly mbts.tasks.TaskSecurityEyeData eye_data;
public readonly bool is_eye_cross;
public NMSheetTaskEyeData(bool is_on, double edge, double size) {
this.is_on = is_on;
this.edge = edge;
this.size = size;
public NMSheetTaskEyeData(mbts.tasks.TaskSecurityEyeData eye_data, bool is_eye_cross) {
this.eye_data = eye_data;
this.is_eye_cross = is_eye_cross;
}
}
@@ -7,7 +7,6 @@ using System.Threading.Tasks;
using bts.api;
using mbts.spark;
using mbts.ui;
namespace BCG {
public class NMSheetDataCoalescer : IDisposable {
@@ -32,12 +31,12 @@ namespace BCG {
_bbo_data_source = new NMSheetBBODataSource(threaded_bb, nmsheet_symbol_list, () => { _is_dirty = true; });
_ticker_data_source = new NMSheetTickerDataSource(threaded_bb, nmsheet_symbol_list, req_id, () => { _is_dirty = true; });
_presaved_theos_provider = new NMSheetPresavedTheosProvider(threaded_bb, nmsheet_symbol_list, req_id);
_threaded_bb.subscribe(SparkTags.TC2Tags.TaskData);
//_threaded_bb.add_to_subscription_list(TaskingTags.ConsolidatedDataTag);
_threaded_bb.data_callback += _on_bb_update;
}
private void _on_bb_update(object tag, object data) {
if (SparkTags.TC2Tags.TaskData.Equals(tag) || _in_bb_settings_tag.Equals(tag))
if (/*TaskingTags.ConsolidatedDataTag.Equals(tag) ||*/ _in_bb_settings_tag.Equals(tag))
_is_dirty = true;
}
@@ -45,9 +44,9 @@ namespace BCG {
if (_is_dirty) {
_is_dirty = false;
_timer.start();
NMSheetAllTaskingData d = _threaded_bb.read_state(
SparkTags.TC2Tags.TaskData, new NMSheetAllTaskingData());
NMSheetData rv = new NMSheetData(_main_data_source.get_data(), _bbo_data_source.get_all_data(), _ticker_data_source.get_data(), d);
TaskingConsolidatedData d = null;//_threaded_bb.sec_thread_retrieve_from_cache (TaskingTags.ConsolidatedDataTag) as TaskingConsolidatedData;
NMSheetData rv = new NMSheetData(_main_data_source.get_data(), _bbo_data_source.get_all_data(), _ticker_data_source.get_data(),
d ?? TaskingConsolidatedData.empty);
rv = _filter_data(rv, _threaded_bb.read_state(_in_bb_settings_tag));
_timer.stop();
_stats_logger.log(String.Format("NMSheetDataCoalescer_{0}", _req_id), "NMSheetData.cons", _timer.lastIntervalTime);
+25 -8
View File
@@ -1,10 +1,12 @@
using mbts.analytics;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace BCG {
using Size = System.Single;
public enum BidAskAlertZone { buy, sell, none }
public class BBOPacket {
public enum MarketSide {
@@ -13,8 +15,8 @@ namespace BCG {
private double _bid_price => md.bid_price;
private double _ask_price => md.ask_price;
private Size _bid_size => md.bid_size;
private Size _ask_size => md.ask_size;
private UInt32 _bid_size => md.bid_size;
private UInt32 _ask_size => md.ask_size;
private static BBOPacket _null_pack = new BBOPacket(VolSurfaceMDUnit.empty);
public readonly VolSurfaceMDUnit md;
@@ -22,6 +24,21 @@ namespace BCG {
this.md = md;
}
public static bool bid_through_theo(BBOPacket md, mbts.spark.TheoPoint tp, bool is_call) {
return false;
// if (tp != null && md != null && md._md_row != null)
// return get_bid_price(md) > (is_call ? tp.call : tp.put);
// else
// return false;
}
public static bool ask_through_theo(BBOPacket md, mbts.spark.TheoPoint tp, bool is_call) {
// if (tp != null && md != null && md._md_row != null)
// return get_ask_price(md) < (is_call ? tp.call : tp.put);
// else
return false;
}
public static double get_mid_price(BBOPacket md) {
return (get_bid_price(md) + get_ask_price(md)) / 2.0;
}
@@ -30,16 +47,16 @@ namespace BCG {
return md != null ? md._bid_price : Double.NaN;
}
public static Size get_bid_size(BBOPacket md) {
return md != null ? md._bid_size : (Size)0;
public static UInt32 get_bid_size(BBOPacket md) {
return md != null ? md._bid_size : (UInt32)0;
}
public static double get_ask_price(BBOPacket md) {
return md != null ? md._ask_price : Double.NaN;
}
public static Size get_ask_size(BBOPacket md) {
return md != null ? md._ask_size : (Size)0;
public static UInt32 get_ask_size(BBOPacket md) {
return md != null ? md._ask_size : (UInt32)0;
}
}
}
@@ -0,0 +1,58 @@
using ProtoBuf;
using System;
namespace mbts.tasks {
[ProtoContract(Name = "ElectronicTradingTask")]
[Serializable]
public class ElectronicTradingTask {
[ProtoBuf.ProtoMember(10)]
public readonly TaskCommon common = null;
[ProtoBuf.ProtoMember(20)]
public readonly ExplicitTask explicit_task = null;
[ProtoBuf.ProtoMember(30)]
public readonly ImplicitTask implicit_task = null;
private ElectronicTradingTask() { }
public ElectronicTradingTask(TaskCommon common, ExplicitTask task) {
// Logger.assert(common != null);
// Logger.assert(task != null);
this.common = common;
this.explicit_task = task;
this.implicit_task = null;
}
public ElectronicTradingTask(TaskCommon common, ImplicitTask task) {
// Logger.assert(common != null);
// Logger.assert(task != null);
this.common = common;
this.explicit_task = null;
this.implicit_task = task;
}
public ElectronicTradingTask with(TaskCommon common) {
return explicit_task == null ?
new ElectronicTradingTask(common, implicit_task) :
new ElectronicTradingTask(common, explicit_task);
}
public ElectronicTradingTask with(TaskCommon common = null, ExplicitTask explicit_task = null) {
return new ElectronicTradingTask(common ?? this.common, explicit_task ?? this.explicit_task);
}
public ElectronicTradingTask with(TaskCommon common = null, ImplicitTask implicit_task = null) {
return new ElectronicTradingTask(common ?? this.common, explicit_task ?? this.explicit_task);
}
public override string ToString() {
return common.id;
}
}
public class QuickStartElectronicTradingTask {
private readonly ElectronicTradingTask _task;
public QuickStartElectronicTradingTask(TaskCommon common, ExplicitTask task) {
_task = new ElectronicTradingTask(common, task);
}
public static implicit operator ElectronicTradingTask(QuickStartElectronicTradingTask task) {
return task._task;
}
}
}
@@ -0,0 +1,159 @@
using ProtoBuf;
using System;
using System.Collections.Generic;
namespace mbts.tasks {
[Serializable]
//[RecordType]
[ProtoContract(Name = "TaskCommon")]
public class TaskCommon {
[ProtoMember(1)]
public readonly string session;
[ProtoMember(10)]
public readonly string id;
[ProtoMember(20)]
public readonly DateTime create_time;
[ProtoMember(30)]
public readonly TaskType task_type;
[ProtoMember(40)]
public readonly string name;
[ProtoMember(50)]
public readonly TaskEdgeType edge_type;
[ProtoMember(60)]
public readonly string edge_surface;
[ProtoMember(70)]
public readonly double bid_edge_param;
[ProtoMember(75)]
public readonly double ask_edge_param;
[ProtoMember(80)]
public readonly double bid_size_param;
[ProtoMember(85)]
public readonly double ask_size_param;
[ProtoMember(90)]
public readonly TaskExitCondition exit_condition;
[ProtoMember(100)]
public readonly double exit_condition_parameter;
[ProtoMember(110)]
public readonly bool rfq_only;
[ProtoMember(120)]
public readonly double rfq_quote_for_seconds;
[ProtoMember(130)]
public readonly TaskSide side;
[ProtoMember(140)]
public readonly DateTime last_modification_time;
[ProtoMember(150)]
public readonly bool auto_hedge;
//[ProtoMember(160)]
//public readonly bool auto_start;
[ProtoMember(200)]
public readonly List<Tuple<int, double>> overridden_edges;
[ProtoMember(210)]
public readonly List<Tuple<int, uint>> overridden_sizes;
private TaskCommon() { /*for protobuf*/ }
public TaskCommon(string id,
string session,
DateTime create_time,
TaskType task_type,
string task_name,
TaskExitCondition exit_condition,
double exit_condition_param,
bool rfq_only,
double rfq_quote_for_seconds,
TaskEdgeType edge_type,
string edge_surface,
double bid_edge_param,
double ask_edge_param,
double bid_size_param,
double ask_size_param,
TaskSide side,
DateTime last_modification_time,
bool auto_hedge,
List<Tuple<int, double>> overridden_edges,
List<Tuple<int, uint>> overridden_sizes) {
this.id = id;
this.session = session;
this.create_time = create_time;
this.task_type = task_type;
this.name = task_name;
this.exit_condition = exit_condition;
this.exit_condition_parameter = exit_condition_param;
this.rfq_only = rfq_only;
this.rfq_quote_for_seconds = rfq_quote_for_seconds;
this.edge_type = edge_type;
this.edge_surface = edge_surface;
this.bid_edge_param = bid_edge_param;
this.ask_edge_param = ask_edge_param;
this.bid_size_param = bid_size_param;
this.ask_size_param = ask_size_param;
this.side = side;
this.last_modification_time = last_modification_time;
this.auto_hedge = auto_hedge;
this.overridden_edges = overridden_edges;
this.overridden_sizes = overridden_sizes;
}
public static TaskCommon Default {
get {
return new TaskCommon(
id: Guid.NewGuid().ToString(),
session: String.Empty,
create_time: DateTime.Now,
task_type: TaskType.Quoter,
task_name: "",
exit_condition: TaskExitCondition.Contracts,
exit_condition_param: 100,
rfq_only: false,
rfq_quote_for_seconds: 10,
edge_type: TaskEdgeType.Manual,
edge_surface: "",
bid_edge_param: double.NaN,
ask_edge_param: double.NaN,
bid_size_param: double.NaN,
ask_size_param: double.NaN,
side: TaskSide.Buy | TaskSide.Sell,
last_modification_time: DateTime.Now,
auto_hedge: true,
overridden_edges: new List<Tuple<int, double>>(),
overridden_sizes: new List<Tuple<int, uint>>());
}
}
public TaskCommon with(string id = null, string session = null, DateTime? create_time = null,
TaskType? task_type = null, string name = null, TaskExitCondition? exit_condition = null,
double? exit_condition_parameter = null, bool? rfq_only = null, double? rfq_quote_for_seconds = null, TaskEdgeType? edge_type = null,
string edge_surface = null,
double? bid_edge_param = null, double? bid_size_param = null,
double? ask_edge_param = null, double? ask_size_param = null,
TaskSide? side = null, DateTime? last_modification_time = null,
bool? auto_hedge = null,
List<Tuple<int, double>> overridden_edges = null,
List<Tuple<int, uint>> overridden_sizes = null) {
return new TaskCommon(id ?? this.id,
session ?? this.session,
create_time ?? this.create_time,
task_type ?? this.task_type,
name ?? this.name,
exit_condition ?? this.exit_condition,
exit_condition_parameter ?? this.exit_condition_parameter,
rfq_only ?? this.rfq_only,
rfq_quote_for_seconds ?? this.rfq_quote_for_seconds,
edge_type ?? this.edge_type,
edge_surface ?? this.edge_surface,
bid_edge_param ?? this.bid_edge_param,
ask_edge_param ?? this.ask_edge_param,
bid_size_param ?? this.bid_size_param,
ask_size_param ?? this.ask_size_param,
side ?? this.side,
last_modification_time ?? this.last_modification_time,
auto_hedge ?? this.auto_hedge,
overridden_edges ?? this.overridden_edges,
overridden_sizes ?? this.overridden_sizes);
}
}
}
@@ -0,0 +1,70 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace mbts.tasks
{
/// Task persisted state combined with
/// the live running state
public class TaskLiveData : IEquatable<TaskLiveData>
{
public readonly ElectronicTradingTask task;
public readonly TaskSwitchState switch_state;
public readonly TaskHealthState task_state;
public readonly double net_accumulation, abs_accumulation;
public TaskLiveData(ElectronicTradingTask task, TaskSwitchState switch_state, TaskHealthState health_state,
double net_accumulation, double abs_accumulation)
{
this.task = task;
this.switch_state = switch_state;
this.task_state = health_state;
this.net_accumulation = net_accumulation;
this.abs_accumulation = abs_accumulation;
}
public string task_id { get { return task.common.id; } }
public TaskType task_type { get { return task.common.task_type; } }
public string name { get { return task.common.name; } }
public double completion_ratio { get { return abs_accumulation / task.common.exit_condition_parameter; } }
public bool is_filled { get { return completion_ratio >= 1.0; } }
public DateTime modification_time { get { return task.common.last_modification_time; } }
public TaskLiveData with(ElectronicTradingTask task = null, TaskSwitchState? switch_state = null, TaskHealthState? task_state = null,
double? net_accumulation = null, double? abs_accumulation = null)
{
return new TaskLiveData(task ?? this.task,
switch_state ?? this.switch_state,
task_state ?? this.task_state,
net_accumulation ?? this.net_accumulation,
abs_accumulation ?? this.abs_accumulation);
}
public int GetHashCode(TaskLiveData obj) { return obj.task_id.GetHashCode(); }
public bool Equals(TaskLiveData other)
{
return ReferenceEquals(task, other.task) &&
switch_state == other.switch_state &&
task_state == other.task_state &&
completion_ratio == other.completion_ratio;
}
public override string ToString()
{
return task.ToString();
}
public string get_summary_text()
{
string sign = task.common.side == TaskSide.Buy ? "+" : (task.common.side == TaskSide.Sell ? "-" : "+/-");
return String.Format("{0}{1} ({2}/{3})", sign, task.common.name, abs_accumulation, task.common.exit_condition_parameter);
}
}
}
@@ -0,0 +1,50 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace mbts.tasks {
public class TaskSecurityEyeData {
public TaskSecurityEyeData() {
}
public bool is_output_present {
get {
return false;
}
}
public bool is_on {
get {
return false;
}
}
/// If the security is on, returns the edge as sent by the eye
/// otherwise returns the input edge
public double edge {
get {
return Double.NaN;
}
}
/// If the security is on, returns the size as sent by the eye
/// otherwise returns the input size
public uint size {
get {
return 0;
}
}
public double eye_published_price {
get {
// if (is_on && is_output_present)
// return input.secside_key.side == bts.o2.msgs.Side.type.BUY ? output.price - output.edge : output.price + output.edge;
// return Double.NaN;
return Double.NaN;
}
}
}
}
@@ -48,3 +48,53 @@ namespace mbts.engine {
}
}
}
namespace BCG {
public class TaskingConsolidatedData {
public TaskingConsolidatedData(IEnumerable<TaskLiveData> input_tasks,
object input_securities,
object eye_output,
object quoter_output) {
}
public readonly static TaskingConsolidatedData empty = new TaskingConsolidatedData(Enumerable.Empty<TaskLiveData>(),
null, null, null);
// public TaskingConsolidatedData with(IEnumerable<TaskLiveData> input_tasks = null,
// IEnumerable<TaskSecurityData> input_securities = null,
// IEnumerable<EyeSecurityState> eye_output = null,
// IEnumerable<QuoterSecurityState> quoter_output = null) {
// return new TaskingConsolidatedData(input_tasks ?? this._input_tasks, input_securities ?? this._input_securities,
// eye_output ?? _eye_output, quoter_output ?? _quoter_output);
// }
public IEnumerable<TaskLiveData> get_tasks(TaskType task_type) { return new TaskLiveData[] { }; }
public TaskLiveData get_task_by_name(TaskType task_type, string name) {
IEnumerable<TaskLiveData> live_tasks = get_tasks(task_type);
return live_tasks.FirstOrDefault(lt => lt.task.common.name == name);
}
public IEnumerable<TaskLiveData> get_security_owning_tasks(IEnumerable<SecuritySideKey> secside_keys, TaskType t_type) {
HashSet<TaskLiveData> rv = new HashSet<TaskLiveData>();
return rv;
}
public HashSet<uint> get_set_securities(TaskType task_type, bool is_on_only = false) {
return new HashSet<uint>();
}
public TaskSecurityEyeData get_eye_data(uint key, Side side) { return get_eye_data(new SecuritySideKey(key, side)); }
public TaskSecurityEyeData get_eye_data(SecuritySideKey key) {
return new TaskSecurityEyeData();
}
public TaskSecurityQuoterData get_quoter_data(uint key, Side side) { return get_quoter_data(new SecuritySideKey(key, side)); }
public TaskSecurityQuoterData get_quoter_data(SecuritySideKey key) {
return new TaskSecurityQuoterData();
}
public TaskLiveData get_security_task(SecuritySideKey key, TaskType task_type) {
return null;
}
}
}
@@ -87,21 +87,21 @@ namespace BCG {
}
private void _refresh_task_data(uint seckey) {
// string eye_task_text = String.Empty, quoter_task_text = String.Empty;
// bool dummy, is_bid, is_ask;
// NMSheetSettingColumnOrganization.parse_column(_last_mousemove_cell.col, out dummy, out dummy, out is_bid, out is_ask);
// if (is_bid ^ is_ask) {
// TaskingConsolidatedData task_data = _sheet_data.get_task_data();
// mbts.tasks.TaskLiveData eye_task_ld = task_data != null ? task_data.get_security_task(new mbts.engine.SecuritySideKey(seckey, is_bid ? Side.Buy : Side.Sell), mbts.tasks.TaskType.Eye) : null;
// if (eye_task_ld != null)
// eye_task_text = String.Format("Eye '{0}' {1} {2}", eye_task_ld.name, eye_task_ld.switch_state.ToString().ToUpper(),
// eye_task_ld.abs_accumulation.ToString("0") + "/" + eye_task_ld.task.common.exit_condition_parameter.ToString("0"));
// mbts.tasks.TaskLiveData quoter_task_ld = task_data != null ? task_data.get_security_task(new mbts.engine.SecuritySideKey(seckey, is_bid ? Side.Buy : Side.Sell), mbts.tasks.TaskType.Quoter) : null;
// if (quoter_task_ld != null)
// quoter_task_text += String.Format("Quoter '{0}' {1} {2}", quoter_task_ld.name, quoter_task_ld.switch_state.ToString().ToUpper(),
// quoter_task_ld.abs_accumulation.ToString("0") + "/" + quoter_task_ld.task.common.exit_condition_parameter.ToString("0"));
// }
// _set_text_visibility(_statusbar_toolstripstatus_task, true, String.Format("{0}{1}{2}", eye_task_text, String.IsNullOrEmpty(eye_task_text) ? String.Empty : " ", quoter_task_text));
string eye_task_text = String.Empty, quoter_task_text = String.Empty;
bool dummy, is_bid, is_ask;
NMSheetSettingColumnOrganization.parse_column(_last_mousemove_cell.col, out dummy, out dummy, out is_bid, out is_ask);
if (is_bid ^ is_ask) {
TaskingConsolidatedData task_data = _sheet_data.get_task_data();
mbts.tasks.TaskLiveData eye_task_ld = task_data != null ? task_data.get_security_task(new mbts.engine.SecuritySideKey(seckey, is_bid ? Side.Buy : Side.Sell), mbts.tasks.TaskType.Eye) : null;
if (eye_task_ld != null)
eye_task_text = String.Format("Eye '{0}' {1} {2}", eye_task_ld.name, eye_task_ld.switch_state.ToString().ToUpper(),
eye_task_ld.abs_accumulation.ToString("0") + "/" + eye_task_ld.task.common.exit_condition_parameter.ToString("0"));
mbts.tasks.TaskLiveData quoter_task_ld = task_data != null ? task_data.get_security_task(new mbts.engine.SecuritySideKey(seckey, is_bid ? Side.Buy : Side.Sell), mbts.tasks.TaskType.Quoter) : null;
if (quoter_task_ld != null)
quoter_task_text += String.Format("Quoter '{0}' {1} {2}", quoter_task_ld.name, quoter_task_ld.switch_state.ToString().ToUpper(),
quoter_task_ld.abs_accumulation.ToString("0") + "/" + quoter_task_ld.task.common.exit_condition_parameter.ToString("0"));
}
_set_text_visibility(_statusbar_toolstripstatus_task, true, String.Format("{0}{1}{2}", eye_task_text, String.IsNullOrEmpty(eye_task_text) ? String.Empty : " ", quoter_task_text));
}
private static void _set_text_visibility(System.Windows.Forms.ToolStripStatusLabel l, bool new_visibility, string new_text) {
@@ -0,0 +1,99 @@
using mbts;
using mbts.tasks;
using System;
using System.Drawing;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
namespace BCG {
partial class NMSheetControl {
//private bool _task_quoter_enabled = true;
private void _init_task_quoter_ui() {
// _task_quoter_enabled = true;
// if (_task_quoter_enabled)
// _disable_task_quoter_submenus();
// else
// _toolstripmenuitem_task_quoter.Enabled = false;
// _toolstripmenuitem_settings_show_task_quoter_data.Click += (s, e) => _get_toolstripmenuitem_display_state_and_publish(_toolstripmenuitem_settings_show_task_quoter_data,
// NMSheetSettingColumnOrganization.get_cols_for_type(NMSheetColumnType.Quoter).ToArray());
}
private void _disable_task_quoter_submenus() {
// _toolstripmenuitem_task_quoter.Enabled = _toolstripmenuitem_task_quoter_add_buys_to_task.Enabled =
// _toolstripmenuitem_task_quoter_add_sells_to_task.Enabled = _toolstripmenuitem_task_quoter_add_buys_and_sells_to_task.Enabled = false;
// _toolstripmenuitem_task_quoter_add_buys_to_task.DropDownItems.Clear();
// _toolstripmenuitem_task_quoter_add_sells_to_task.DropDownItems.Clear();
// _toolstripmenuitem_task_quoter_add_buys_and_sells_to_task.DropDownItems.Clear();
// List<ToolStripItem> create_menu_items = new List<ToolStripItem>();
// foreach (ToolStripItem ti in _toolstripmenuitem_task_quoter.DropDownItems)
// if (_create_menu_tag.Equals(ti.Tag))
// create_menu_items.Add(ti);
// create_menu_items.ForEach(ti => _toolstripmenuitem_task_quoter.DropDownItems.Remove(ti));
}
private void _adapt_contextmenu_for_tasks_quoter() {
// if (_task_quoter_enabled) {
// _disable_task_quoter_submenus();
// if (_task_selection.is_active) {
// _toolstripmenuitem_task_quoter.Enabled = true;
// ///Create
// IEnumerable<TaskCommon> templates = _threaded_bb.sec_thread_retrieve_from_cache(TaskingTags.TemplatesTag) as IEnumerable<TaskCommon>;
// templates = templates == null || templates.Count() == 0 ? new TaskCommon[] { TaskCommon.Default.with(name: "New Task") } : templates;
// double min_strike = _task_selection.strikes.Min(), max_strike = _task_selection.strikes.Max();
// string name = TaskType.Quoter.ToString() + " " +
// _task_selection.exp.get_display_text() + " " +
// (min_strike == max_strike ? min_strike.ToString("0.00") : String.Format("{0} - {1}", min_strike.ToString("0.00"), max_strike.ToString("0.00")));
// int add_task_index = 0;
// foreach (TaskCommon t in templates) {
// ToolStripMenuItem add_task_item = new ToolStripMenuItem(t.name, null, (s, e) => {
// mbts.tasks.TaskCommon common_task = t.with(task_type: TaskType.Quoter, name: name, side: TaskSide.None, id: Guid.NewGuid().ToString());
// ExplicitTask explicit_task = ExplicitTask.Default.with(securities: _task_selection.keys, security_descriptions: _task_selection.names);
// _threaded_bb.sec_thread_write(TaskingTags.ShowCreateTask, new ElectronicTradingTask(common_task, explicit_task));
// });
// add_task_item.Tag = _create_menu_tag;
// add_task_item.Enabled = true;
// _toolstripmenuitem_task_quoter.DropDownItems.Insert(add_task_index++, add_task_item);
// }
// //Add Buys to
// TaskingConsolidatedData task_data = _sheet_data.get_task_data();
// _toolstripmenuitem_task_quoter_add_buys_to_task.Enabled = true;
// IEnumerable<TaskLiveData> tasks = task_data.get_tasks(TaskType.Quoter).OrderBy(t => t.name);
// foreach (TaskLiveData t in tasks) {
// ElectronicTradingTask mod_task = _get_mod_task(t.task, _task_selection);
// ToolStripMenuItem add_item = new ToolStripMenuItem(t.get_summary_text(), null, (s, e) => _threaded_bb.sec_thread_write(TaskingTags.ShowEditTask, mod_task));
// add_item.Enabled = t.task.common.side != TaskSide.Sell;
// _toolstripmenuitem_task_quoter_add_buys_to_task.DropDownItems.Add(add_item);
// }
// /// Add Sells to
// _toolstripmenuitem_task_quoter_add_sells_to_task.Enabled = true;
// foreach (TaskLiveData t in tasks) {
// ElectronicTradingTask mod_task = _get_mod_task(t.task, _task_selection);
// ToolStripMenuItem add_item = new ToolStripMenuItem(t.get_summary_text(), null, (s, e) => _threaded_bb.sec_thread_write(TaskingTags.ShowEditTask, mod_task));
// add_item.Enabled = t.task.common.side != TaskSide.Buy;
// _toolstripmenuitem_task_quoter_add_sells_to_task.DropDownItems.Add(add_item);
// }
// /// Add Buys/Sells to
// _toolstripmenuitem_task_quoter_add_buys_and_sells_to_task.Enabled = true;
// foreach (TaskLiveData t in tasks) {
// ElectronicTradingTask mod_task = _get_mod_task(t.task, _task_selection);
// ToolStripMenuItem add_item = new ToolStripMenuItem(t.get_summary_text(), null, (s, e) => _threaded_bb.sec_thread_write(TaskingTags.ShowEditTask, mod_task));
// add_item.Enabled = t.task.common.side == (TaskSide.Buy | TaskSide.Sell);
// _toolstripmenuitem_task_quoter_add_buys_and_sells_to_task.DropDownItems.Add(add_item);
// }
// }
// }
}
// private ElectronicTradingTask _get_task_quoter_mod_task(ElectronicTradingTask task) {
// List<uint> secs = new List<uint>(task.explicit_task.securities);
// List<string> secs_desc = new List<string>(task.explicit_task.security_descriptions);
// secs.AddRange(_task_selection.keys);
// secs_desc.AddRange(_task_selection.names);
// ElectronicTradingTask mod_task = task.with(explicit_task: task.explicit_task.with(securities: secs, security_descriptions: secs_desc));
// return mod_task;
// }
}
}
@@ -83,25 +83,26 @@ namespace BCG {
}
private bool _get_ee_switch_override(NMSheetSettings settings, MyAlertHelperData helper_data, int exp_index, int strike_index, ref Color out_color) {
if (!helper_data.is_theo)
return false;
NMSheetRowAuxiliaryData aux_data = _formatted_theos.get_aux_data(exp_index, strike_index);
if (aux_data == null)
return false;
NMSheetCallPutBidAskWrapper<NMSheetTaskEyeData> t_data = aux_data.task_ee_data;
if (t_data == null)
return false;
NMSheetTaskEyeData bid_sec_t_data =
t_data.get_data(helper_data.is_call ? bts.api.PutOrCall.Call : bts.api.PutOrCall.Put,
bts.api.Side.Buy);
NMSheetTaskEyeData ask_sec_t_data =
t_data.get_data(helper_data.is_call ? bts.api.PutOrCall.Call : bts.api.PutOrCall.Put,
bts.api.Side.Sell);
if ((bid_sec_t_data != null && bid_sec_t_data.is_on) ||
(ask_sec_t_data != null && ask_sec_t_data.is_on)) {
out_color = settings.setting_alerts.ee_on_color.HasValue ?
settings.setting_alerts.ee_on_color.Value : Color.DarkGreen;
return true;
if (helper_data.is_ee_set_edge_or_size || helper_data.is_ee_price) {
NMSheetRowAuxiliaryData aux_data = _formatted_theos.get_aux_data(exp_index, strike_index);
if (aux_data != null) {
NMSheetCallPutBidAskWrapper<NMSheetTaskEyeData> eye_data = aux_data.task_ee_data;
if (eye_data != null) {
NMSheetTaskEyeData secside_eye_data = eye_data.get_data(helper_data.is_call, helper_data.is_bid);
if (secside_eye_data != null && secside_eye_data.eye_data != null) {
if (helper_data.is_ee_price) {
if (secside_eye_data.is_eye_cross) {
out_color = _settings.setting_alerts.ee_fire_color.Value;
return true;
}
}
if (secside_eye_data.eye_data.is_on) {
out_color = _settings.setting_alerts.ee_on_color.Value;
return true;
}
}
}
}
}
return false;
}
@@ -29,7 +29,7 @@ namespace mbts.spark {
get {
var m = new OrderMetadata { KeyBinding = string.Empty, NoProps = false };
if (_studio_meta.HasValue && _studio_meta.Value.badge_color.HasValue)
m.Color = _studio_meta.Value.badge_color.Value.to_uint();
m.Color = _studio_meta.Value.badge_color.Value.rgb_color();
return m;
}
}
@@ -136,7 +136,7 @@ namespace mbts.analytics {
IEnumerable<VolSurfaceExpiration> all_exps) {
var exps = all_exps.Where(vse => vse.symbol.is_null_or_empty()).ToArray();
var exp_header_cells = exps
.Select(vse => SecurityFormatter.format_expiration(vse.expiration))
.Select(vse => DateFormatter.Format(vse.expiration, DateFormat.DayMonthAbvDiff2000))
.ToArray();
return (exps, exp_header_cells);
}
@@ -145,7 +145,7 @@ namespace mbts.analytics {
IEnumerable<VolSurfaceExpiration> all_exps) {
var exps = all_exps.ToArray();
var exp_header_cells = exps.Select(vse => string.IsNullOrEmpty(vse.symbol) ?
SecurityFormatter.format_expiration(vse.expiration) : vse.symbol)
DateFormatter.Format(vse.expiration, DateFormat.DayMonthAbvDiff2000) : vse.symbol)
.ToArray();
return (exps, exp_header_cells);
}
@@ -190,24 +190,13 @@ namespace mbts.analytics {
}
}
void _compute_swipe_sum() {
swipe_sum_puts = 0;
swipe_sum_calls = 0;
swipe_sum_net = 0;
foreach (var (row, exps) in _visible_selected_cells) {
foreach (var exp in exps) {
var (p, c, n) = row.get_cell_values(exp);
if (!p.is_nan()) {
swipe_sum_puts += p;
}
if (!c.is_nan()) {
swipe_sum_calls += c;
}
if (!n.is_nan()) {
swipe_sum_net += n;
}
}
}
}
void _compute_swipe_sum() =>
(swipe_sum_puts, swipe_sum_calls, swipe_sum_net) = _visible_selected_cells
.SelectMany(tup =>
tup.exps.Select(exp => {
var (p, c, n) = tup.row.get_cell_values(exp);
return (p.if_nan(0), c.if_nan(0), n.if_nan(0));
}))
.Sum();
}
}
@@ -57,6 +57,8 @@
<analytics:ComboFutureDataColumn x:Key="FutureSymDataColumn" HeaderTemplate="{StaticResource SymHeaderTemplate}" ElementStyle="{StaticResource FutureSymDataElementStyle}" MinWidth="60" x:Shared="False" />
<analytics:ComboOptionDataColumn x:Key="OptionExpDataColumn" HeaderTemplate="{StaticResource ExpHeaderTemplate}" ElementStyle="{StaticResource OptionExpDataElementStyle}" MinWidth="60" x:Shared="False" />
<analytics:ComboOptionDataColumn x:Key="OptionSymDataColumn" HeaderTemplate="{StaticResource SymHeaderTemplate}" ElementStyle="{StaticResource OptionSymDataElementStyle}" MinWidth="60" x:Shared="False" />
<MenuItem x:Key="LaunchConfigurationEditorMenuItem" x:Shared="False" Header="Report Configuration..." Command="{Binding DataContext.launch_configuration_editor, Source={x:Reference ComboWindow}}" />
<MenuItem x:Key="ExportToCSVMenuItem" Header="Export To CSV..." Command="{Binding export_to_csv_command}" CommandParameter="{Binding DataContext.show_call_put, Source={x:Reference ComboWindow}}" />
</UserControl.Resources>
<Grid>
<Grid.RowDefinitions>
@@ -97,7 +99,14 @@
VerticalGridLinesBrush="LightGray"
CanUserResizeColumns="False"
CanUserReorderColumns="False"
IsReadOnly="True" />
IsReadOnly="True"
>
<DataGrid.ContextMenu>
<ContextMenu>
<StaticResourceExtension ResourceKey="LaunchConfigurationEditorMenuItem" />
</ContextMenu>
</DataGrid.ContextMenu>
</c:DataGridEx>
</AdornerDecorator>
<GridSplitter Grid.Row="2" Height="3" Background="Black" HorizontalAlignment="Stretch" />
@@ -135,6 +144,12 @@
<TextBlock Text="{Binding Item.strike, RelativeSource={RelativeSource AncestorType=DataGridRow}}" />
</DataTemplate>
</DataGrid.RowHeaderTemplate>
<DataGrid.ContextMenu>
<ContextMenu>
<StaticResourceExtension ResourceKey="LaunchConfigurationEditorMenuItem" />
<StaticResourceExtension ResourceKey="ExportToCSVMenuItem" />
</ContextMenu>
</DataGrid.ContextMenu>
</c:DataGridEx>
</AdornerDecorator>
@@ -1,7 +1,5 @@
#nullable enable
namespace mbts.analytics {
using bts.api;
using System;
using System.Diagnostics.Contracts;
@@ -19,9 +17,13 @@ namespace mbts.analytics {
symbol = null;
}
private static string _format_exp(DateTime exp) {
return mbts.ui.utility.ExpirationFormatter.DateFormatter.format_day_month_year(exp);
}
SlideGreekUnitKey(DateTime exp_date) {
exp = exp_date;
_unique_name = SecurityFormatter.format_expiration(exp_date);
_unique_name = _format_exp(exp_date);
type = GroupType.Exp;
symbol = null;
}
@@ -29,7 +31,7 @@ namespace mbts.analytics {
SlideGreekUnitKey(DateTime exp_date, string symbol) {
exp = exp_date;
this.symbol = symbol;
_unique_name = $"{SecurityFormatter.format_expiration(exp_date)}:{symbol}";
_unique_name = $"{_format_exp(exp_date)}:{symbol}";
type = GroupType.SymExp;
}
+22 -33
View File
@@ -1,7 +1,6 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>net7.0-windows</TargetFramework>
<TargetFramework>net6.0-windows</TargetFramework>
<UseWPF>true</UseWPF>
<Authors>Blue Trading Systems</Authors>
<Company>Blue Trading Systems</Company>
@@ -22,39 +21,34 @@
<RootNamespace>bts</RootNamespace>
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<WarningsAsErrors />
<Version>$(major).$(minor).$(patch)</Version>
<Version Condition="'$(version)'=='..'">1.0.0</Version>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="CommandLineParser" Version="2.9.1" />
<PackageReference Include="GitVersion.MsBuild" Version="5.12.0">
<IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
<PrivateAssets>all</PrivateAssets>
</PackageReference>
<PackageReference Include="Google.Protobuf" Version="3.24.3" />
<PackageReference Include="IronPython" Version="3.4.1" />
<PackageReference Include="MathNet.Numerics" Version="5.0.0" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.2.0" />
<PackageReference Include="NAudio" Version="2.0.1" />
<PackageReference Include="NUnit" Version="3.13.3" />
<PackageReference Include="NUnit3TestAdapter" Version="4.2.1" />
<PackageReference Include="Newtonsoft.Json" Version="13.0.1" />
<PackageReference Include="OxyPlot.Core" Version="2.1.2" />
<PackageReference Include="OxyPlot.Wpf" Version="2.1.2" />
<PackageReference Include="protobuf-net" Version="3.2.26" />
<PackageReference Include="System.Composition" Version="7.0.0-preview.2.22152.2" />
<PackageReference Include="System.Composition.AttributedModel" Version="7.0.0-preview.2.22152.2" />
<PackageReference Include="System.Composition.Hosting" Version="7.0.0-preview.2.22152.2" />
<PackageReference Include="System.Composition.TypedParts" Version="7.0.0-preview.2.22152.2" />
<PackageReference Include="System.Reactive" Version="6.0.0" />
<PackageReference Include="System.Reactive.Core" Version="6.0.0" />
<PackageReference Include="System.Reactive.Interfaces" Version="6.0.0" />
<PackageReference Include="System.Reactive.Linq" Version="6.0.0" />
<PackageReference Include="System.Reactive.PlatformServices" Version="6.0.0" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\spark_api\spark_api.csproj" />
<ProjectReference Include="..\spark_core\spark_core.csproj" />
<PackageReference Include="System.Reactive.Core" Version="5.0.0" />
<PackageReference Include="System.Reactive.Interfaces" Version="5.0.0" />
<PackageReference Include="System.Reactive.Linq" Version="5.0.0" />
<PackageReference Include="System.Reactive.PlatformServices" Version="5.0.0" />
<PackageReference Include="System.Runtime.Experimental" Version="6.0.2" />
<PackageReference Include="CommandLineParser" Version="2.9.1" />
<ProjectReference Include="../spark_api/spark_api.csproj" />
<ProjectReference Include="../spark_core/spark_core.csproj" />
<PackageReference Include="Google.Protobuf" Version="3.21.4" />
<PackageReference Include="IronPython" Version="2.7.12" />
<PackageReference Include="NAudio" Version="2.0.1" />
<PackageReference Include="Newtonsoft.Json" Version="13.0.1" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.2.0" />
<PackageReference Include="NUnit" Version="3.13.3" />
<PackageReference Include="NUnit3TestAdapter" Version="4.2.1" />
<PackageReference Include="System.Reactive" Version="5.0.0" />
<PackageReference Include="protobuf-net" Version="3.1.17" />
<PackageReference Include="OxyPlot.Core" Version="2.1.2" />
<PackageReference Include="OxyPlot.Wpf" Version="2.1.2" />
</ItemGroup>
<ItemGroup>
@@ -62,20 +56,15 @@
<Resource Include="**/*.png" />
<ConfigDefaults Include="../../lib/config/defaults/*.conf" />
</ItemGroup>
<ItemGroup>
<Resource Remove="logo.ico" />
</ItemGroup>
<ItemGroup>
<Content Include="logo.ico" />
</ItemGroup>
<ItemGroup>
<EmbeddedResource Include="Sounds/game_sound_correct.wav" />
<EmbeddedResource Include="Sounds/whistle.wav" />
</ItemGroup>
<Target Name="diagnostic" AfterTargets="PreBuildEvent" />
</Project>
@@ -71,8 +71,7 @@ namespace BCG {
foreach (string sym in temp.Keys) {
SortedList<DateTime, string> temp2 = temp[sym];
foreach (KeyValuePair<DateTime, string> kvp in temp2) {
string datecode = bts.api.SecurityFormatter.format_expiration(
kvp.Key, date_format: bts.api.DateFormat.MonthCodeLastDigitYear);
string datecode = bts.api.DateFormatter.Format(kvp.Key, bts.api.DateFormat.MonthCodeLastDigitYear);
string explegs = (temp.Keys.Count > 1) ? string.Concat(sym, datecode, "_", kvp.Value) :
string.Concat(datecode, "_", kvp.Value);
@@ -61,7 +61,7 @@ namespace BCG {
string rv = String.Empty;
foreach (SingleSpreadLeg l in legs)
rv += (rv == String.Empty ? "" : "/") + l.symbol + //BCG.Utilities.Dates.DateCode.getMonthSymbol(l.exp) + (l.exp.Year - 2000);
SecurityFormatter.format_expiration(l.exp);
bts.api.DateFormatter.Format(l.exp, bts.api.DateFormat.DayMonthAbvDiff2000);
return rv;
}
-2
View File
@@ -366,8 +366,6 @@ namespace mbts.spark {
public class Nothing { Nothing() { } }
public class TC2Tags {
public static ITag<NMSheetAllTaskingData> TaskData { get; } =
_mk_tag<NMSheetAllTaskingData>();
// Data request for a sheet
// Published by NMSheetDriverControlStrip
public static ITag<NMSheetDataRequest> NMSheetDataRequestTag(string id) =>
@@ -253,7 +253,6 @@ namespace mbts.ui {
public static BTSColor foreground => UI.default_foreground;
public static BTSColor anchor => Colors.Gold;
public static BTSColor profit => Colors.Green;
public static BTSColor net_zero => BTSCoreColors.gray;
public static BTSColor loss => BTSCoreColors.venetian_red;
public static BTSColor header_row_background => 0xffaaaaaa;
// group background colors
@@ -17,7 +17,7 @@ namespace bts.proto {
readonly double _opacity;
public ColorOpacityProto(Color color = default, double opacity = 1.0)
: this(color.to_uint(), opacity) { }
: this(color.rgb_color(), opacity) { }
public ColorOpacityProto(uint color = 0u, double opacity = 1.0) {
_color = color;
@@ -16,7 +16,7 @@ namespace bts.proto {
readonly bool _show;
public ColorShowProto(Color value, bool show = true)
: this(value.to_uint(), show) { }
: this(value.rgb_color(), show) { }
public ColorShowProto(uint value, bool show = true) {
_value = value;
@@ -0,0 +1,51 @@
using bts.api;
using bts.utils;
using mbts.utils;
using ProtoBuf;
using System;
namespace bts.proto {
[ProtoContract]
public struct ExpDate : IEquatable<ExpDate> {
[ProtoMember(1)]
readonly uint _month;
[ProtoMember(2)]
readonly uint _year;
[ProtoMember(3)]
readonly uint _day;
public ExpDate(SecurityImmutable security)
: this(security.earliest_expiration()) { }
public ExpDate(DateTime date) {
_month = (uint)date.Month;
_year = (uint)date.Year;
_day = (uint)date.Day;
}
public uint month => _month;
public uint year => _year;
public uint day => _day;
public bool Equals(ExpDate other) =>
other._month == _month && other._year == year && other._day == day;
public override bool Equals(object obj) => obj is ExpDate ed && Equals(ed);
public static bool operator ==(ExpDate a, ExpDate b) => a.Equals(b);
public static bool operator !=(ExpDate a, ExpDate b) => !a.Equals(b);
public override int GetHashCode() =>
EqualityComparer.aggregate_hash((int)_month, (int)_day, (int)_year);
public override string ToString() =>
DateFormatter.Format((int)_year, (int)_month, (int)_day, DateFormat.MonthCodeLastDigitYear);
}
static class ExpDateExtensions {
public static DateTime to_date_time(this ExpDate exp_date) =>
new DateTime((int)exp_date.year, (int)exp_date.month, (int)exp_date.day);
}
}
@@ -1,42 +1,36 @@
#nullable enable
using bts.utils;
using mbts.ui;
using ProtoBuf;
using System;
using System.Windows.Media;
namespace bts.proto {
using bts.utils;
using mbts.ui;
using ProtoBuf;
using System;
using System.Diagnostics.CodeAnalysis;
using System.Windows.Media;
[ProtoContract]
readonly struct NullableColorProto : IEquatable<NullableColorProto> {
struct NullableColorProto : IEquatable<NullableColorProto> {
[ProtoMember(1)]
readonly uint? _value;
public NullableColorProto(Color? value) =>
_value = value?.to_uint();
_value = value?.rgb_color();
public static NullableColorProto none => new(null);
public NullableColorProto(uint value) =>
_value = value;
public Color? value => _value?.argb_color();
[MemberNotNullWhen(true, nameof(value))]
public bool has_value => value.HasValue;
public Color? value => _value?.rgb_color();
public Color? argb => _value?.argb_color();
public bool Equals(NullableColorProto other) =>
EqualityComparer.nullable_equals(_value, other._value);
public override bool Equals(object? obj) =>
public override bool Equals(object obj) =>
obj is NullableColorProto ncp && Equals(ncp);
public override int GetHashCode() =>
_value.HasValue ? (int)_value.Value : 0;
public override string ToString() =>
_value?.ToString() ?? string.Empty;
public static bool operator ==(NullableColorProto a, NullableColorProto b) => a.Equals(b);
public static bool operator !=(NullableColorProto a, NullableColorProto b) => !a.Equals(b);
}
@@ -0,0 +1,42 @@
using bts.utils;
using mbts.utils;
using ProtoBuf;
using System;
using System.Windows;
namespace mbts.ui.settings {
[ProtoContract]
struct NullableFontWeightProto : IEquatable<NullableFontWeightProto> {
[ProtoMember(1)]
readonly ushort? _value;
public NullableFontWeightProto(FontWeight? value) =>
_value = (ushort?)value?.ToOpenTypeWeight();
public NullableFontWeightProto(ushort value) =>
_value = value;
public FontWeight? value {
get {
if (_value.HasValue)
return FontWeight.FromOpenTypeWeight(_value.Value);
return null;
}
}
public bool Equals(NullableFontWeightProto other) =>
EqualityComparer.nullable_equals(_value, other._value);
public override bool Equals(object obj) =>
obj is NullableFontWeightProto ncp && Equals(ncp);
public override int GetHashCode() =>
_value.HasValue ? _value.Value : 0;
public static bool operator ==(NullableFontWeightProto a, NullableFontWeightProto b) => a.Equals(b);
public static bool operator !=(NullableFontWeightProto a, NullableFontWeightProto b) => !a.Equals(b);
}
}
@@ -1,49 +0,0 @@
#nullable enable
namespace bts.proto {
using bts.utils;
using ProtoBuf;
using System;
using System.Diagnostics.CodeAnalysis;
using System.Windows;
[ProtoContract]
readonly struct NullableFontWeightProto : IEquatable<NullableFontWeightProto> {
[ProtoMember(1)]
readonly int? _value;
public NullableFontWeightProto(FontWeight? value) =>
_value = value?.ToOpenTypeWeight();
public NullableFontWeightProto(int value) =>
_value = value;
public static NullableFontWeightProto none =>
new(null);
public FontWeight? value =>
_value.HasValue ? FontWeight.FromOpenTypeWeight(_value.Value) : null;
[MemberNotNullWhen(true, nameof(value))]
public bool has_value => value.HasValue;
public bool Equals(NullableFontWeightProto other) =>
EqualityComparer.nullable_equals(_value, other._value);
public override bool Equals(object? obj) =>
obj is NullableFontWeightProto fw && Equals(fw);
public override int GetHashCode() =>
_value ?? 0;
public override string ToString() =>
_value?.ToString() ?? string.Empty;
public static bool operator ==(NullableFontWeightProto a, NullableFontWeightProto b) =>
a.Equals(b);
public static bool operator !=(NullableFontWeightProto a, NullableFontWeightProto b) =>
!a.Equals(b);
}
}
@@ -103,7 +103,7 @@ namespace mbts.ui.controls {
color = brush.Color;
opacity = brush.Opacity;
}
public ColorOpacityProto to_proto() => new ColorOpacityProto(color.to_uint(), opacity);
public ColorOpacityProto to_proto() => new ColorOpacityProto(color.rgb_color(), opacity);
}
class NamedColorPickerPopupVM : ColorPickerPopupVM {
@@ -104,7 +104,7 @@ namespace mbts.ui.settings {
public bool is_expanded => _is_expanded;
public FontWeight? font_weight_override => _font_weight_override.value;
public Color? font_color_override => _font_color_override.value;
public Color? background_color_override => _background_color_override.value;
public Color? background_color_override => _background_color_override.argb;
public double width => _width;
public HorizontalAlignment horizontal_alignment => _horizontal_alignment;
public double horizontal_offset => _horizontal_offset;
@@ -126,7 +126,7 @@ namespace mbts.ui.settings {
width ?? this.width,
horizontal_alignment ?? this.horizontal_alignment,
horizontal_offset ?? this.horizontal_offset,
(background_color_override ?? _background_color_override).value);
(background_color_override ?? _background_color_override).argb);
public GridColumnSettings Clone() =>
ProtobufSerializationHelper.clone(this);
@@ -23,7 +23,7 @@
public static GridSettings Default =>
new GridSettings(
selection_highlight: Colors.MediumSlateBlue.with(0x63).to_uint(),
selection_highlight: Colors.MediumSlateBlue.with(0x63).argb_color(),
background: BTSColors.Grid.default_column_background,
font_color: BTSColors.Grid.default_column_foreground);
@@ -149,7 +149,7 @@ namespace mbts.ui.settings {
var a = sl.A.within_range((byte)30, (byte)200);
if (sl.A != a) {
sl.A = a;
new_settings = settings.with(selection_highlight: sl.to_uint());
new_settings = settings.with(selection_highlight: sl.rgb_color());
return true;
}
}
@@ -137,9 +137,9 @@ namespace mbts.spark {
foreach (IGrouping<TPredicateData, CellAnimation> g in animations)
animation_map.AddOrUpdate(g.Key, p => animation_tuple(c: g), (p, t) => t.cell_animations.AddRange(g));
}
return _create_settings_obj(new GridSettings(font_family.name(), font_size, font_weight, font_color.color.to_uint(), selection_highlight.color.to_uint(), col_settings,
return _create_settings_obj(new GridSettings(font_family.name(), font_size, font_weight, font_color.color.rgb_color(), selection_highlight.color.rgb_color(), col_settings,
background: background_color.color.with(
(byte)(background_color.opacity.within_range(0, 1) * 255.0)).to_uint()),
(byte)(background_color.opacity.within_range(0, 1) * 255.0)).rgb_color()),
animation_map.Select(kv => PredicateAnimations.create_data<TRowData, TPredicateData>(kv.Key, kv.Value.cell_animations, kv.Value.row_animations, kv.Value.sounds)));
//
(List<RowAnimation> row_animations, List<SoundNotification> sounds, List<CellAnimation> cell_animations) animation_tuple(IEnumerable<RowAnimation> r = null, IEnumerable<SoundNotification> s = null, IGrouping<TPredicateData, CellAnimation> c = null) =>
@@ -120,10 +120,10 @@ namespace mbts.spark {
font_family.name(),
font_size,
font_weight,
font_color.color.to_uint(),
selection_highlight.color.to_uint(),
font_color.color.rgb_color(),
selection_highlight.color.rgb_color(),
columns.Select(c => c.create()),
background: background_color.color.to_uint());
background: background_color.color.argb_color());
public void load_from(GridSettings value) {
if (value == null)
@@ -258,13 +258,13 @@ namespace mbts.spark {
settings.title_font_params = new() {
typeface = new(title_font_family, title_font_weight.ToOpenTypeWeight()),
font_size = title_font_size,
font_color = title_font_color.to_uint(),
font_color = title_font_color.argb_color(),
};
settings.font_params = new() {
typeface = new(font_family, font_weight.ToOpenTypeWeight()),
font_size = font_size,
font_color = font_color.to_uint(),
font_color = font_color.argb_color(),
};
}
@@ -42,7 +42,6 @@
<TextBlock
x:Name="PART_Context"
FontWeight="Bold"
Foreground="{u:BTSBrush UI.default_text}"
HorizontalAlignment="Left"
Margin="4,0,0,0"
Text="{Binding context}"
@@ -5,7 +5,6 @@ namespace mbts.ui.controls {
using System;
using System.Diagnostics.CodeAnalysis;
using System.Numerics;
static class TickUpDownHelper {
public const string
@@ -14,7 +13,7 @@ namespace mbts.ui.controls {
public static string? format<T>(
T? new_value, string curr_text, TickDisplaySettingsImmutable? settings = null)
where T : struct, IFloatingPointIeee754<T> {
where T : struct, IFloatingPoint<T> {
if (T.TryParse(curr_text, null, out var from_text)) {
if (!from_text.Equals(new_value)) {
return format(new_value, settings);
@@ -26,7 +25,7 @@ namespace mbts.ui.controls {
}
public static string format<T>(T? value, TickDisplaySettingsImmutable? settings = null)
where T : struct, IFloatingPointIeee754<T> {
where T : struct, IFloatingPoint<T> {
if (!value.HasValue) {
return string.Empty;
}
@@ -40,7 +39,7 @@ namespace mbts.ui.controls {
string? text,
[NotNullWhen(true)] out T? result,
TickDisplaySettingsImmutable? settings = null
) where T : IFloatingPointIeee754<T> {
) where T : IFloatingPoint<T> {
if (text is null) {
result = default;
return false;
@@ -11,7 +11,6 @@ namespace mbts.ui.controls {
using System;
using System.Linq;
using System.Numerics;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Input;
@@ -3,14 +3,13 @@ using System.Collections;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Threading;
using System.Windows.Data;
namespace mbts.ui.converters {
class DictionaryLookupConverter : IMultiValueConverter {
[ThreadStatic]
Dictionary<Type, Lookup> _type_impls_backing;
Dictionary<Type, Lookup> _type_impls =>
Interlocked.CompareExchange(ref _type_impls_backing, new(), null);
Dictionary<Type, Lookup> _type_impls => _type_impls_backing ?? (_type_impls_backing = new Dictionary<Type, Lookup>());
delegate bool Lookup(object source, object key, out object result);
@@ -22,11 +22,16 @@ namespace mbts.ui.converters {
object value, Type target_type, object parameter, CultureInfo culture) =>
throw new NotImplementedException();
public string convert(SecurityExpiration exp) =>
SecurityFormatter.format_expiration(
exp.expiration,
ShowSymbol ? exp.symbol : null,
ShowType ? exp.security_type.contract_case() : null,
DateFormat);
public string convert(SecurityExpiration exp) {
var sb = new StringBuilder();
if (ShowType) {
sb.Append($"[{SecurityFormatter.format_security_type(exp.security_type)}] ");
}
if (ShowSymbol) {
sb.Append(exp.symbol);
}
sb.Append(DateFormatter.Format(exp.expiration, DateFormat));
return sb.ToString();
}
}
}
@@ -114,7 +114,10 @@ namespace mbts.ui {
public static SolidColorBrush rgb_solid_brush(this uint color) =>
new SolidColorBrush(rgb_color(color));
public static uint to_uint(this Color color) =>
public static UInt32 argb_color(this Color color) =>
(uint)color.A << 24 | (uint)color.R << 16 | (uint)color.G << 8 | (uint)color.B;
public static UInt32 rgb_color(this Color color) =>
(uint)color.A << 24 | (uint)color.R << 16 | (uint)color.G << 8 | (uint)color.B;
public static Brush to_brush(this Color color) =>
@@ -9,7 +9,6 @@
using Spark.Core.Disposables;
using System;
using System.Numerics;
using System.Reactive.Linq;
using System.Windows.Input;
@@ -7,7 +7,6 @@ using Spark.Core.Disposables;
using System;
using System.Collections.Generic;
using System.Numerics;
using System.Reactive.Linq;
namespace mbts.ui {
@@ -162,7 +162,7 @@
// Compare bids
if (direct.int_price == implied.int_price) {
bid[x] = new NativePriceSize(direct.int_price, direct.size_f, implied.size_f);
bid[x] = new NativePriceSize(direct.int_price, direct.size, implied.size);
dbid_idx++;
ibid_idx++;
}
@@ -185,7 +185,7 @@
// Compare asks
if (direct.int_price == implied.int_price) {
ask[x] = new NativePriceSize(direct.int_price, direct.size_f, implied.size_f);
ask[x] = new NativePriceSize(direct.int_price, direct.size, implied.size);
dask_idx++;
iask_idx++;
}
@@ -1,15 +1,14 @@
namespace mbts.co2 {
using System.Runtime.InteropServices;
using Size = System.Single;
[StructLayout(LayoutKind.Sequential)]
public readonly struct NativePriceLevel {
readonly IntPrice _bid;
readonly IntPrice _ask;
readonly Size _bid_size;
readonly Size _ask_size;
readonly uint _bid_size;
readonly uint _ask_size;
public NativePriceLevel(IntPrice bid, Size bid_size, IntPrice ask, Size ask_size) {
public NativePriceLevel(IntPrice bid, uint bid_size, IntPrice ask, uint ask_size) {
_bid = bid;
_bid_size = bid_size;
_ask = ask;
@@ -5,29 +5,27 @@ namespace mbts.co2 {
using System;
using System.Runtime.InteropServices;
using Size = System.Single;
public readonly struct NativePriceSize : IEquatable<NativePriceSize> {
readonly IntPrice _price;
readonly Size _size;
readonly Size _direct_size;
readonly uint _size;
readonly uint _direct_size;
static NativePriceSize() =>
Log.assert(Marshal.SizeOf<NativePriceSize>() == 16);
public NativePriceSize(IntPrice price, Size size) {
public NativePriceSize(IntPrice price, uint size) {
_price = price;
_size = size;
_direct_size = size;
}
public NativePriceSize(long mantissa, sbyte exponent, Size size) {
public NativePriceSize(long mantissa, sbyte exponent, uint size) {
_price = new IntPrice(mantissa, exponent);
_size = size;
_direct_size = size;
}
public NativePriceSize(IntPrice price, Size direct_size, Size implied_size) {
public NativePriceSize(IntPrice price, uint direct_size, uint implied_size) {
_price = price;
_size = direct_size + implied_size;
_direct_size = direct_size;
@@ -38,18 +36,15 @@ namespace mbts.co2 {
public IntPrice int_price => _price;
public long mantissa => _price.mantissa;
public sbyte exponent => _price.exponent;
public uint size => (uint)_size;
public uint direct_size => (uint)_direct_size;
public uint implied_size => (uint)(_size - _direct_size);
public Size size_f => _size;
public Size direct_size_f => _direct_size;
public Size implied_size_f => _size - _direct_size;
public uint size => _size;
public uint direct_size => _direct_size;
public uint implied_size => _size - _direct_size;
public double price => _price.price();
public bool is_nan => _price.is_nan;
public override string ToString() =>
$"{price} {size_f} ({implied_size})";
$"{price} {size} ({implied_size})";
public override bool Equals(object obj) =>
obj is NativePriceSize p ? Equals(p) : base.Equals(obj);
+4 -5
View File
@@ -3,14 +3,13 @@ using mbts.co2;
namespace bts.md
{
using Size = System.Single;
public class PriceSize
{
public Size size { get; }
public Size direct_size { get; }
public Size implied_size { get; }
public uint size { get; }
public uint direct_size { get; }
public uint implied_size { get; }
public double price { get; }
public PriceSize(Size sz, Size direct_sz, Size implied_sz, double prx)
public PriceSize(uint sz, uint direct_sz, uint implied_sz, double prx)
{
size = sz;
direct_size = direct_sz;
@@ -1,216 +1,192 @@
using Google.Protobuf.WellKnownTypes;
using Google.Protobuf;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Reactive.Linq;
using System.IO;
using System.Reactive.Disposables;
using mbts;
using System.Threading;
namespace bts.api.core {
internal class QuickbusClientChannel : ClientChannel {
IntPtr _client;
public QuickbusClientChannel(ServiceContext context, string type_name, string qualifier) : base(context) {
_client = ApiNativeMethods.api_client_create(context.native_context, type_name, qualifier);
System.Diagnostics.Trace.Assert(_client != IntPtr.Zero);
}
public override void Dispose() {
ApiNativeMethods.api_client_destroy(_client);
_client = IntPtr.Zero;
}
int _req_id = 0;
Dictionary<int, PBCallbackWrapper> _keepalive_cache = new();
unsafe public override Task<Result<Response>> send<Request, Response>(int method_id, Request request) {
var id = Interlocked.Increment(ref _req_id);
var header = new RequestHeader() {
Method = method_id,
RequestId = id,
Token = _context.token.HasValue ? new AuthToken() { Token = _context.token?.Token } : null
};
var buffer = header.serialize(request);
var tcs = new TaskCompletionSource<Result<Response>>();
//ApiNativeMethods.api_client_log_error($"Call {id}");
ApiNativeMethods.raw_pb_callback callback = (rbuffer, rlength, _) => {
//ApiNativeMethods.api_client_log_error($"Reply {id}");
var res = ApiUtils.deserialize<ResponseHeader, Response>(rbuffer, (long)rlength);
if (res.header.Code == ApiError.Success) {
tcs.TrySetResult(new Result<Response>(res.body));
}
else {
tcs.TrySetResult(new Result<Response>(res.header.Code));
}
lock (_keepalive_cache) {
_keepalive_cache.Remove(id);
}
};
System.Diagnostics.Trace.Assert(_client != IntPtr.Zero, "Channel may have been disposed");
var cb_wrapper = new PBCallbackWrapper(callback);
lock (_keepalive_cache) {
_keepalive_cache.Add(id, cb_wrapper);
}
ApiNativeMethods.api_client_send(
_client, buffer, buffer.Length, cb_wrapper.callback, IntPtr.Zero);
return tcs.Task;
}
public override IObservable<RawUpdate<TOut>> subscribe<TParse,TOut>(int method_id, string method, string qualifier, MessageParser<TParse> parser, Func<TParse,TOut> converter) {
var result = Observable.Create<RawUpdate<TOut>>(async observer => {
IntPtr temp_subscription = IntPtr.Zero;
void unsubscribe_temp_sub() {
// Unsubscribe late to keep qb refcount > 0 continuously
if (temp_subscription != IntPtr.Zero) ApiNativeMethods.api_client_unsubscribe(_client, temp_subscription);
}
// 'tcs' and 'temp_callback' are defined in the same scope as 'temp_subscription'
// (rather than in the 'while loop' scope) to prevent premature garbage collection
TaskCompletionSource<bool> tcs = null;
ApiNativeMethods.raw_subscription_callback temp_callback =
(event_type, changes, change_count, unused) => {
tcs?.TrySetResult(true);
};
while (true) {
var response = await check_stream_access(method_id, qualifier);
if (response.success) {
if (response.value.Authorized) {
// success. Break loop and subscribe
break;
}
else {
// Not authorized. return empty stream
unsubscribe_temp_sub();
observer.OnCompleted();
return System.Reactive.Disposables.Disposable.Empty;
}
}
else {
// Wait for stream to fire once before trying again
unsubscribe_temp_sub();
tcs = new TaskCompletionSource<bool>();
temp_subscription = ApiNativeMethods.api_client_subscribe(
_client, method, qualifier, temp_callback, IntPtr.Zero);
await tcs.Task;
}
}
// Authorized. Stream events
unsubscribe_temp_sub();
// Ensure 'temp_callback' and 'tcs' aren't Garbage Collected before 'temp_subscription'
// is disposed
GC.KeepAlive(temp_callback);
GC.KeepAlive(tcs);
return SubscribeNative(method, qualifier, parser, converter, observer);
});
Log.QBus.diag($"Subscribing for sub: '{method}/{qualifier}'");
return result;
}
private Task<Result<StreamAccessResponse>> check_stream_access(int method_id, string qualifier) {
var request = new StreamAccessRequest() { Qualifier = qualifier ?? "" };
return send<StreamAccessRequest, StreamAccessResponse>(method_id, request);
}
private unsafe IDisposable SubscribeNative<TParse, TOut>(string method, string qualifier, MessageParser<TParse> parser, Func<TParse, TOut> converter, IObserver<RawUpdate<TOut>> observer) where TParse : IMessage<TParse> {
bool first_update = true;
// Memory optimization. There is only one update per subscription.
RawUpdate<TOut> the_update = new RawUpdate<TOut>();
ApiNativeMethods.raw_subscription_callback cb = (event_type, changes, change_count, unused) => {
the_update.Clear();
try {
if (event_type == ApiNativeMethods.EventType.TABLE_UPDATED) {
if (changes != null) {
foreach (var change in changes) {
switch (change.type) {
case ApiNativeMethods.ChangeType.REMOVE:
the_update.removed_keys.Add(change.key);
break;
case ApiNativeMethods.ChangeType.REPLACE:
the_update.changed_items.Add(converter(parser.ParseFrom(new UnmanagedMemoryStream(change.buffer, change.buffer_len))));
the_update.changed_keys.Add(change.key);
break;
case ApiNativeMethods.ChangeType.CREATE:
the_update.added_items.Add(converter(parser.ParseFrom(new UnmanagedMemoryStream(change.buffer, change.buffer_len))));
the_update.added_keys.Add(change.key);
break;
}
}
}
observer.OnNext(the_update);
}
else if (event_type == ApiNativeMethods.EventType.TABLE_CREATED) {
if (!first_update) {
observer.OnNext(the_update.MarkAsReset());
}
first_update = false;
}
}
catch (Exception e) {
ApiNativeMethods.api_client_log_error($"Exception in subscription callback for sub: '{method}/{qualifier}' \n--\n '{e}'");
// Sleep to let the log message get asyncronously written to disk
Thread.Sleep(100);
Environment.Exit(-1);
}
};
var subscription = ApiNativeMethods.api_client_subscribe(_client, method, qualifier, cb, IntPtr.Zero);
return FinalizeableAnonymousDisposable.Create((disposing) => {
Log.QBus.diag($"Unsubscribing for sub: '{method}/{qualifier}'");
ApiNativeMethods.api_client_unsubscribe(_client, subscription);
subscription = IntPtr.Zero;
GC.KeepAlive(cb);
cb = null;
});
}
private class FinalizeableAnonymousDisposable : IDisposable {
private Action<bool> _action;
public FinalizeableAnonymousDisposable(Action<bool> dispose) {
_action = dispose;
}
public static FinalizeableAnonymousDisposable Create(Action<bool> dispose) { return new FinalizeableAnonymousDisposable(dispose); }
~FinalizeableAnonymousDisposable() {
Dispose(false);
}
public void Dispose() {
GC.SuppressFinalize(this);
Dispose(true);
}
protected virtual void Dispose(bool disposing) {
var temp = _action;
_action = null;
temp?.Invoke(disposing);
}
}
public override bool is_sync_call_ok() {
return !ApiNativeMethods.api_client_is_on_qb_thread(_client);
}
/// <summary>
/// A simple wrapper that can be used to prevent the premature garbage collection of a
/// <see cref="ApiNativeMethods.raw_pb_callback"/> delegate.
/// </summary>
/// <remarks>
/// This is part of a workaround for an apparent bug in csharp's GarbageCollector, where the
/// final reference to a delegate instance mustn't be removed until any and all execution has
/// finished (even if the reference is removed by the delegate's last statemwent, a
/// garbage-collector race may yield the infamous error, "A callback was made on a garbage
/// collected delegate of type...").
/// </remarks>
class PBCallbackWrapper {
public readonly ApiNativeMethods.raw_pb_callback callback;
public PBCallbackWrapper(ApiNativeMethods.raw_pb_callback callback) =>
this.callback = callback;
}
}
}
using Google.Protobuf.WellKnownTypes;
using Google.Protobuf;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Reactive.Linq;
using System.IO;
using System.Reactive.Disposables;
using mbts;
using System.Threading;
namespace bts.api.core {
internal class QuickbusClientChannel : ClientChannel {
IntPtr _client;
public QuickbusClientChannel(ServiceContext context, string type_name, string qualifier) : base(context) {
_client = ApiNativeMethods.api_client_create(context.native_context, type_name, qualifier);
System.Diagnostics.Trace.Assert(_client != IntPtr.Zero);
}
public override void Dispose() {
ApiNativeMethods.api_client_destroy(_client);
_client = IntPtr.Zero;
}
int _req_id = 0;
Dictionary<int, ApiNativeMethods.raw_pb_callback> _keepalive_cache = new Dictionary<int, ApiNativeMethods.raw_pb_callback>();
unsafe public override Task<Result<Response>> send<Request, Response>(int method_id, Request request) {
var id = Interlocked.Increment(ref _req_id);
var header = new RequestHeader() {
Method = method_id,
RequestId = id,
Token = _context.token.HasValue ? new AuthToken() { Token = _context.token?.Token } : null
};
var buffer = header.serialize(request);
var tcs = new TaskCompletionSource<Result<Response>>();
//ApiNativeMethods.api_client_log_error($"Call {id}");
ApiNativeMethods.raw_pb_callback callback = (rbuffer, rlength, _) => {
//ApiNativeMethods.api_client_log_error($"Reply {id}");
var res = ApiUtils.deserialize<ResponseHeader, Response>(rbuffer, (long)rlength);
if (res.header.Code == ApiError.Success) {
tcs.TrySetResult(new Result<Response>(res.body));
}
else {
tcs.TrySetResult(new Result<Response>(res.header.Code));
}
lock (_keepalive_cache) { _keepalive_cache.Remove(id); }
};
System.Diagnostics.Trace.Assert(_client != IntPtr.Zero, "Channel may have been disposed");
lock (_keepalive_cache) { _keepalive_cache.Add(id, callback); }
ApiNativeMethods.api_client_send(_client, buffer, buffer.Length, callback, IntPtr.Zero);
return tcs.Task;
}
public override IObservable<RawUpdate<TOut>> subscribe<TParse,TOut>(int method_id, string method, string qualifier, MessageParser<TParse> parser, Func<TParse,TOut> converter) {
var result = Observable.Create<RawUpdate<TOut>>(async observer => {
IntPtr temp_subscription = IntPtr.Zero;
void unsubscribe_temp_sub() {
// Unsubscribe late to keep qb refcount > 0 continuously
if (temp_subscription != IntPtr.Zero) ApiNativeMethods.api_client_unsubscribe(_client, temp_subscription);
}
// 'tcs' and 'temp_callback' are defined in the same scope as 'temp_subscription'
// (rather than in the 'while loop' scope) to prevent premature garbage collection
TaskCompletionSource<bool> tcs = null;
ApiNativeMethods.raw_subscription_callback temp_callback =
(event_type, changes, change_count, unused) => {
tcs?.TrySetResult(true);
};
while (true) {
var response = await check_stream_access(method_id, qualifier);
if (response.success) {
if (response.value.Authorized) {
// success. Break loop and subscribe
break;
}
else {
// Not authorized. return empty stream
unsubscribe_temp_sub();
observer.OnCompleted();
return System.Reactive.Disposables.Disposable.Empty;
}
}
else {
// Wait for stream to fire once before trying again
unsubscribe_temp_sub();
tcs = new TaskCompletionSource<bool>();
temp_subscription = ApiNativeMethods.api_client_subscribe(
_client, method, qualifier, temp_callback, IntPtr.Zero);
await tcs.Task;
}
}
// Authorized. Stream events
unsubscribe_temp_sub();
// Ensure 'temp_callback' and 'tcs' aren't Garbage Collected before 'temp_subscription'
// is disposed
GC.KeepAlive(temp_callback);
GC.KeepAlive(tcs);
return SubscribeNative(method, qualifier, parser, converter, observer);
});
Log.QBus.diag($"Subscribing for sub: '{method}/{qualifier}'");
return result;
}
private Task<Result<StreamAccessResponse>> check_stream_access(int method_id, string qualifier) {
var request = new StreamAccessRequest() { Qualifier = qualifier ?? "" };
return send<StreamAccessRequest, StreamAccessResponse>(method_id, request);
}
private unsafe IDisposable SubscribeNative<TParse, TOut>(string method, string qualifier, MessageParser<TParse> parser, Func<TParse, TOut> converter, IObserver<RawUpdate<TOut>> observer) where TParse : IMessage<TParse> {
bool first_update = true;
// Memory optimization. There is only one update per subscription.
RawUpdate<TOut> the_update = new RawUpdate<TOut>();
ApiNativeMethods.raw_subscription_callback cb = (event_type, changes, change_count, unused) => {
the_update.Clear();
try {
if (event_type == ApiNativeMethods.EventType.TABLE_UPDATED) {
if (changes != null) {
foreach (var change in changes) {
switch (change.type) {
case ApiNativeMethods.ChangeType.REMOVE:
the_update.removed_keys.Add(change.key);
break;
case ApiNativeMethods.ChangeType.REPLACE:
the_update.changed_items.Add(converter(parser.ParseFrom(new UnmanagedMemoryStream(change.buffer, change.buffer_len))));
the_update.changed_keys.Add(change.key);
break;
case ApiNativeMethods.ChangeType.CREATE:
the_update.added_items.Add(converter(parser.ParseFrom(new UnmanagedMemoryStream(change.buffer, change.buffer_len))));
the_update.added_keys.Add(change.key);
break;
}
}
}
observer.OnNext(the_update);
}
else if (event_type == ApiNativeMethods.EventType.TABLE_CREATED) {
if (!first_update) {
observer.OnNext(the_update.MarkAsReset());
}
first_update = false;
}
}
catch (Exception e) {
ApiNativeMethods.api_client_log_error($"Exception in subscription callback for sub: '{method}/{qualifier}' \n--\n '{e}'");
// Sleep to let the log message get asyncronously written to disk
Thread.Sleep(100);
Environment.Exit(-1);
}
};
var subscription = ApiNativeMethods.api_client_subscribe(_client, method, qualifier, cb, IntPtr.Zero);
return FinalizeableAnonymousDisposable.Create((disposing) => {
Log.QBus.diag($"Unsubscribing for sub: '{method}/{qualifier}'");
ApiNativeMethods.api_client_unsubscribe(_client, subscription);
subscription = IntPtr.Zero;
GC.KeepAlive(cb);
cb = null;
});
}
private class FinalizeableAnonymousDisposable : IDisposable {
private Action<bool> _action;
public FinalizeableAnonymousDisposable(Action<bool> dispose) {
_action = dispose;
}
public static FinalizeableAnonymousDisposable Create(Action<bool> dispose) { return new FinalizeableAnonymousDisposable(dispose); }
~FinalizeableAnonymousDisposable() {
Dispose(false);
}
public void Dispose() {
GC.SuppressFinalize(this);
Dispose(true);
}
protected virtual void Dispose(bool disposing) {
var temp = _action;
_action = null;
temp?.Invoke(disposing);
}
}
public override bool is_sync_call_ok() {
return !ApiNativeMethods.api_client_is_on_qb_thread(_client);
}
}
}
@@ -11,7 +11,6 @@ namespace mbts {
using System;
using System.Collections.Generic;
using System.Globalization;
using System.Numerics;
public static class TickExtensions {
static string _nan_text => TickDisplaySettings.Default.nan_text;
@@ -110,20 +109,20 @@ namespace mbts {
public static string format_without_decimal_part(this TickFactors tick, double value) =>
format(tick, value, double.NaN, false, _nan_text, true);
public static string format<T>(this TickFactors tick, T value) where T : IFloatingPointIeee754<T> =>
public static string format<T>(this TickFactors tick, T value) where T : IFloatingPoint<T> =>
format(tick, value, T.NaN, false, _nan_text);
public static string format<T>(this TickFactors tick, T value, bool show_commas)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
format(tick, value, T.NaN, show_commas, _nan_text);
public static string format<T>(this TickDisplaySettings settings, T value)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
format(settings.tick_factors, value, settings);
public static string format<T>(
this bts.api.domain.TickDisplaySettingsImmutable settings, T value)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
settings.to_tick_display_settings().format(value);
public static string format<T>(this TickFactors tick, T value, TickDisplaySettings settings)
@@ -150,7 +149,7 @@ namespace mbts {
bool show_commas,
string nan_text,
bool show_decimal_part = true)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
tick.format(
value,
TickDisplaySettings.Default.with(
@@ -197,7 +196,7 @@ namespace mbts {
parse(display_settings.tick_factors, text, display_settings);
public static T parse<T>(this TickDisplaySettings display_settings, string text)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
parse<T>(display_settings.tick_factors, text, display_settings);
#nullable disable
@@ -205,7 +204,7 @@ namespace mbts {
parse<double>(tick, text, display_settings);
public static T parse<T>(this TickFactors tick, string text, TickDisplaySettings display_settings)
where T : IFloatingPointIeee754<T> {
where T : IFloatingPoint<T> {
if (display_settings is null) {
return parse(tick, text, T.NaN, _nan_text);
}
@@ -214,9 +213,7 @@ namespace mbts {
return parse(tick, text, display_multiplier, nan_text);
}
public static T parse<T>(
this TickFactors tick, string text, T display_multiplier, string nan_text)
where T : IFloatingPointIeee754<T> =>
public static T parse<T>(this TickFactors tick, string text, T display_multiplier, string nan_text) where T : IFloatingPoint<T> =>
tick?.is_valid() ?? false ?
_parse(tick, text, display_multiplier, nan_text) :
_parse_no_tick(text, display_multiplier, nan_text);
@@ -226,37 +223,37 @@ namespace mbts {
string text,
T display_multiplier,
string nan_text
) where T : IFloatingPointIeee754<T> =>
) where T : IFloatingPoint<T> =>
regional_tick.is_valid() ?
_parse(regional_tick, text, display_multiplier, nan_text) :
_parse_no_tick(text, display_multiplier, nan_text);
public static T tick<T>(this TickFactors tick, T value, int count)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
count < 0 ? tick.tickdown(value, (uint)-count) : tick.tickup(value, (uint)count);
public static T tick<T>(this bts.api.domain.TickFactorsImmutable tick, T value, int count)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
tick.to_tick_factors().tick(value, count);
public static T tick<T>(
this bts.api.domain.TickDisplaySettingsImmutable settings, T value, int count)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
settings.HasTickFactors ?
settings.TickFactors.tick(value, count) :
throw new ArgumentException(
"Can't tick because 'settings.HasTickFactors' is false", nameof(settings));
public static T tickup<T>(this TickFactors tick, T input, uint count = 1)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
tickup(tick, input, count, TickUtils.precision_const<T>());
public static T tickup<T>(this TickFactors tick, T input, uint count, T precision)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
tickup<T, NumericCastOutConverter<T>>(tick, input, count, precision);
public static T tickup<T, TFromUInt32>(this TickFactors tick, T input, uint count, T precision)
where T : IFloatingPointIeee754<T>
where T : IFloatingPoint<T>
where TFromUInt32 : IConverter<uint, T> {
if (!precision.is_real_positive()) {
throw new ArgumentException("Must be a real positive number.", nameof(precision));
@@ -265,7 +262,7 @@ namespace mbts {
return input;
}
var tuf = tick.tick_unit_frac<T>();
var ieeer = T.Ieee754Remainder(input, tuf);
var ieeer = T.IEEERemainder(input, tuf);
input -= ieeer;
if (ieeer < -precision) {
count--;
@@ -274,18 +271,15 @@ namespace mbts {
return _round_tick(tuf, result);
}
public static T tickup<T>(
this RegionalTickFactors regional_tick, T input) where T : IFloatingPointIeee754<T> =>
public static T tickup<T>(this RegionalTickFactors regional_tick, T input) where T : IFloatingPoint<T> =>
regional_tick.tickup(input, 1);
public static T tickup<T>(
this RegionalTickFactors regional_tick, T input, uint count)
where T : IFloatingPointIeee754<T> =>
public static T tickup<T>(this RegionalTickFactors regional_tick, T input, uint count) where T : IFloatingPoint<T> =>
regional_tick.tickup(input, count, TickUtils.precision_const<T>());
public static T tickup<T>(
this RegionalTickFactors regional_tick, T input, uint count, T precision)
where T : IFloatingPointIeee754<T> {
where T : IFloatingPoint<T> {
if (!precision.is_real_positive()) {
throw new ArgumentException("Must be a real positive number.", nameof(precision));
}
@@ -298,7 +292,7 @@ namespace mbts {
T ltie = regional_tick.low_tick_inclusive_end.as_type<double, T>();
if (input < ltie) {
tuf = regional_tick.low_tick.tick_unit_frac<T>();
var ieeer = T.Ieee754Remainder(input, tuf);
var ieeer = T.IEEERemainder(input, tuf);
input -= ieeer;
if (ieeer < -precision) count--;
val = input + tuf * count.as_type<uint, T>();
@@ -309,7 +303,7 @@ namespace mbts {
}
} else {
tuf = regional_tick.high_tick.tick_unit_frac<T>();
var ieeer = T.Ieee754Remainder(input, tuf);
var ieeer = T.IEEERemainder(input, tuf);
input -= ieeer;
if (ieeer < -precision) count--;
val = input + tuf * count.as_type<uint, T>();
@@ -318,21 +312,21 @@ namespace mbts {
}
public static T tickdown<T>(this TickFactors tick, T input, uint count = 1)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
tickdown(tick, input, count, TickUtils.precision_const<T>());
public static T tickdown<T>(this TickFactors tick, T input, uint count, T precision)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T> =>
tickdown<T, NumericCastOutConverter<T>>(tick, input, count, precision);
public static T tickdown<T, TFromUInt32>(this TickFactors tick, T input, uint count, T precision)
where T : IFloatingPointIeee754<T>
where T : IFloatingPoint<T>
where TFromUInt32 : IConverter<uint, T> {
if (!input.is_real()) {
return input;
}
var tuf = tick.tick_unit_frac<T>();
var ieeer = T.Ieee754Remainder(input, tuf);
var ieeer = T.IEEERemainder(input, tuf);
input -= ieeer;
if (ieeer > precision) {
count--;
@@ -342,22 +336,21 @@ namespace mbts {
}
public static T tickdown<T>(this RegionalTickFactors regional_tick, T input)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T>, IComparisonOperators<T, double> =>
regional_tick.tickdown(input, 1);
public static T tickdown<T>(this RegionalTickFactors regional_tick, T input, uint count)
where T : IFloatingPointIeee754<T> =>
where T : IFloatingPoint<T>, IComparisonOperators<T, double> =>
tickdown(regional_tick, input, count, TickUtils.precision_const<T>());
public static T tickdown<T>(
this RegionalTickFactors regional_tick, T input, uint count, T precision)
where T : IFloatingPointIeee754<T> =>
this RegionalTickFactors regional_tick, T input, uint count, T precision) where T : IFloatingPoint<T> =>
tickdown<T, NumericCastOutConverter<T>, NumericCastOutConverter<T>, NumericCastInConverter<T>>(
regional_tick, input, count, precision);
public static T tickdown<T, TFromUInt32, TFromDouble, TToUInt16>(
this RegionalTickFactors regional_tick, T input, uint count, T precision)
where T : IFloatingPointIeee754<T>
where T : IFloatingPoint<T>
where TFromDouble : IConverter<double, T>
where TFromUInt32 : IConverter<uint, T>
where TToUInt16 : IConverter<T, uint> {
@@ -372,7 +365,7 @@ namespace mbts {
T low_tick_inclusive_end = TFromDouble.convert(regional_tick.low_tick_inclusive_end);
if (input > low_tick_inclusive_end) {
tuf = regional_tick.high_tick.tick_unit_frac<T>();
var ieeer = T.Ieee754Remainder(input, tuf);
var ieeer = T.IEEERemainder(input, tuf);
input -= ieeer;
if (ieeer > precision) count--;
val = input - tuf * TFromDouble.convert(count);
@@ -384,7 +377,7 @@ namespace mbts {
}
} else {
tuf = regional_tick.low_tick.tick_unit_frac<T>();
var ieeer = T.Ieee754Remainder(input, tuf);
var ieeer = T.IEEERemainder(input, tuf);
input -= ieeer;
if (ieeer > precision) count--;
val = input - tuf * TFromDouble.convert(count);
@@ -490,7 +483,7 @@ namespace mbts {
return display_digits(tick.tick_base);
}
public static int display_digits<T>(T tick_base) where T : IFloatingPoint<T>, ILogarithmicFunctions<T> {
public static int display_digits<T>(T tick_base) where T : IFloatingPoint<T> {
var log_tick_base = T.Log10(tick_base);
var floor = T.Floor(log_tick_base);
var dec = log_tick_base - floor;
@@ -507,14 +500,14 @@ namespace mbts {
}
static string _format_no_tick<T>(T value, T display_multiplier, bool show_commas)
where T : INumberBase<T> {
where T : IFloatingPoint<T> {
if (!display_multiplier.is_nan()) {
value *= display_multiplier;
}
return value.ToString(show_commas ? "#,0" : "0", null);
}
static T _parse_no_tick<T>(string text, T display_multiplier, string nan_text) where T : IFloatingPointIeee754<T> {
static T _parse_no_tick<T>(string text, T display_multiplier, string nan_text) where T : IFloatingPoint<T> {
if (text == nan_text) {
return T.NaN;
}
@@ -522,7 +515,7 @@ namespace mbts {
result.safe_divide(display_multiplier) : T.NaN;
}
static T _get_integer_part<T>(string integer_text) where T : IFloatingPointIeee754<T> {
static T _get_integer_part<T>(string integer_text) where T : IFloatingPoint<T> {
if (integer_text.is_null_or_white_space()) {
return T.Zero;
}
@@ -531,7 +524,7 @@ namespace mbts {
result : T.NaN;
}
static T _get_numerator_part<T>(string numerator_text, T tick_base) where T : IFloatingPointIeee754<T> {
static T _get_numerator_part<T>(string numerator_text, T tick_base) where T : IFloatingPoint<T> {
if (string.IsNullOrEmpty(numerator_text)) {
return T.Zero;
}
@@ -561,7 +554,7 @@ namespace mbts {
static T _parse<T>(
RegionalTickFactors regional_tick, string text, T display_multiplier, string nan_text)
where T : IFloatingPointIeee754<T> {
where T : IFloatingPoint<T> {
T result = _parse(regional_tick.low_tick, text, display_multiplier, nan_text);
T ltie = regional_tick.low_tick_inclusive_end.as_type<double, T>()
@@ -573,7 +566,7 @@ namespace mbts {
}
static T _parse<T>(TickFactors tick, string text, T display_multiplier, string nan_text)
where T : IFloatingPointIeee754<T> {
where T : IFloatingPoint<T> {
if (text.is_null_or_white_space() || text == nan_text) {
return T.NaN;
}
@@ -591,7 +584,7 @@ namespace mbts {
}
static T _parse<T>(TickFactors tick, T integer_part, string numerator_part_text)
where T : IFloatingPointIeee754<T> {
where T : IFloatingPoint<T> {
T tick_base = tick.tick_base.as_type<double, T>();
T numerator_part = _get_numerator_part(numerator_part_text, tick_base);
return integer_part + numerator_part / tick_base;
@@ -664,7 +657,7 @@ namespace mbts {
}
}
static T _round_tick<T>(T tick_unit_frac, T input) where T : IFloatingPointIeee754<T> =>
input - T.Ieee754Remainder(input, tick_unit_frac);
static T _round_tick<T>(T tick_unit_frac, T input) where T : IFloatingPoint<T> =>
input - T.IEEERemainder(input, tick_unit_frac);
}
}
@@ -9,7 +9,6 @@ using Spark.Core;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Numerics;
namespace mbts.spark {
static class TickUtils {
@@ -33,6 +33,13 @@
public static string Format(DateTime date, DateFormat format) =>
Format(date.Year, date.Month, date.Day, format);
/// <summary>
/// Returns a concise string representation of a date (using single-letter month codes)
/// appropriate for UIs (e.g. March 22, 2019: 22 Mar 19, or 22 H19).
/// </summary>
public static string Format(uint year, uint month, uint day, DateFormat format) =>
Format((int)year, (int)month, (int)day, format);
/// <summary>
/// Returns a concise string representation of a date (using single-letter month codes)
/// appropriate for UIs (e.g. March 22, 2019: 22 Mar 19, or 22 H19).
@@ -10,9 +10,6 @@ namespace bts.api {
public partial class Security {
public static security_key key(Security s) { return s.Id; }
public static bool is_perpetual_exp(DateTime exp) =>
exp.Year < 2000 || exp.Year > 2999;
public static class Defaults {
public static ContractSpecification ContractSpecification =>
new() {
@@ -1,7 +1,6 @@
namespace bts.api {
using System;
using System.Linq;
using System.Reflection.Metadata.Ecma335;
public static class SecurityExtensions {
public static Security.ContractOneofCase contract_case(this SecurityType type) =>
@@ -97,8 +96,6 @@ namespace bts.api {
return security.Ice.SecurityDesc;
} else if (security.HasDeribit) {
return security.Deribit.SecurityDesc;
} else if (security.HasFtx) {
return security.Ftx.SecurityDesc;
}
Log.assert(false, "security_desc not implemented for exchange");
return null;
@@ -139,7 +136,6 @@ namespace bts.api {
domain.Venue.Bts => Venue.Bts,
domain.Venue.Sim => Venue.Sim,
domain.Venue.Deribit => Venue.Deribit,
domain.Venue.Ftx => Venue.Ftx,
domain.Venue.Glbx => Venue.Glbx,
domain.Venue.None => Venue.Unset,
_ => throw new NotImplementedException(),
@@ -150,7 +146,6 @@ namespace bts.api {
Venue.Bts => domain.Venue.Bts,
Venue.Sim => domain.Venue.Sim,
Venue.Deribit => domain.Venue.Deribit,
Venue.Ftx => domain.Venue.Ftx,
Venue.Glbx => domain.Venue.Glbx,
Venue.Unset => domain.Venue.None,
_ => throw new NotImplementedException(),
@@ -21,7 +21,7 @@
format_future(symbol, (uint)exp.Year, (uint)exp.Month, (uint)exp.Day);
public static string format_future(string symbol, uint exp_year, uint exp_month, uint exp_day) =>
$"{symbol}{format_expiration(new((int)exp_year, (int)exp_month, (int)exp_day))}";
$"{symbol}{DateFormatter.Format(exp_year, exp_month, exp_day, DateFormat.DayMonthAbvDiff2000)}";
public static string format_future(string symbol, FutureContractImmutable future) =>
format_future(symbol, future.ExpirationYear, future.ExpirationMonth, future.ExpirationDay);
@@ -45,7 +45,7 @@
string.IsNullOrEmpty(exch_desc) ? format_option(symbol, option) : exch_desc;
static string _format(SecurityImmutable? security) =>
security.HasValue ? _format(security.Value) : "Unknown-security1";
security.HasValue ? _format(security.Value) : "Unknown-security";
static string _format(SecurityImmutable security, bool exchange_specific_formatting = true) {
switch (security.ContractCase) {
@@ -71,10 +71,8 @@
return string.Join("", _format_legs(new ContractLegEnumerable(security.Spread.Legs, 1)));
case Security.ContractOneofCase.Synthetic:
return security.Synthetic.Name;
case Security.ContractOneofCase.Spot:
return security.security_desc();
default:
return "Unknown-security2";
return "Unknown-security";
}
}
@@ -110,17 +108,12 @@
string? symbol = null,
Security.ContractOneofCase? type = null,
DateFormat date_format = DateFormat.DayMonthAbvDiff2000) {
var result = Security.is_perpetual_exp(exp_date) ?
"Perp" : DateFormatter.Format(exp_date, date_format);
var result = DateFormatter.Format(exp_date, date_format);
if (symbol is not null) {
result = symbol + " " + result;
}
if (type.HasValue) {
if (result.Length == 0) {
result = format_security_type(type.Value);
} else {
result = $"[{format_security_type(type.Value)}] {result}";
}
result = format_security_type(type.Value) + " " + result;
}
return result;
}
+2 -2
View File
@@ -1,6 +1,6 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>net7.0</TargetFramework>
<TargetFramework>net6.0</TargetFramework>
<Authors>Blue Trading Systems</Authors>
<Company>Blue Trading Systems</Company>
<Description />
@@ -11,7 +11,6 @@
<PlatformTarget>x64</PlatformTarget>
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<WarningsAsErrors />
<NoWarn>8981</NoWarn>
<Version>$(major).$(minor).$(patch)</Version>
<Version Condition="'$(version)'=='..'">0.0.0</Version>
</PropertyGroup>
@@ -21,6 +20,7 @@
<PackageReference Include="Google.Protobuf" Version="3.21.4" />
<PackageReference Include="System.Collections.Immutable" Version="5.0.0" />
<PackageReference Include="System.Reactive" Version="5.0.0" />
<PackageReference Include="System.Runtime.Experimental" Version="6.0.2" />
</ItemGroup>
<ItemGroup>
-23
View File
@@ -1,23 +0,0 @@
namespace spark_api_server {
using System;
class Program {
static int Main(string[] args) {
Console.WriteLine("Starting spark_api_server... just checking build");
// TODO
bts.websocket_core.WebsocketDataSync sync =
new bts.websocket_core.WebsocketDataSync();
bts.websocket_core.WebsocketConnectionGateway gwy =
new bts.websocket_core.WebsocketConnectionGateway();
bts.websocket_core.WebsocketServerParams prms = new bts.websocket_core.WebsocketServerParams();
gwy.init(sync);
sync.init(gwy);
gwy.start_listening(prms);
while (true) {
System.Threading.Thread.Sleep(100);
}
//return 0;
}
}
}
@@ -1,20 +0,0 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>net7.0</TargetFramework>
<Nullable>enable</Nullable>
<Platforms>x64</Platforms>
<PlatformTarget>x64</PlatformTarget>
<TreatWarningsAsErrors>true</TreatWarningsAsErrors>
<Version>$(major).$(minor).$(patch)</Version>
<Version Condition="'$(version)'=='..'">0.0.0</Version>
</PropertyGroup>
<ItemGroup>
<ProjectReference Include="../spark_api/spark_api.csproj" />
<ProjectReference Include="../spark_core/spark_core.csproj" />
<ProjectReference Include="../spark_websocket/spark_websocket.csproj" />
</ItemGroup>
</Project>
@@ -61,6 +61,9 @@ namespace System.Collections.Generic {
public static IDictionary<TKey, TValue> as_idictionary<TKey, TValue>(this Dictionary<TKey, TValue> dictionary) =>
dictionary;
public static IReadOnlyDictionary<TKey, TValue> AsReadOnly<TKey, TValue>(this IDictionary<TKey, TValue> dictionary) =>
new ReadOnlyDictionary<TKey, TValue>(dictionary);
public static void Difference<TKey, TValue>(this IDictionary<TKey, TValue> left,
IDictionary<TKey, TValue> right,
out IEnumerable<KeyValuePair<TKey, TValue>> exclusive_left,
@@ -13,7 +13,6 @@ namespace System.Collections.Generic {
using System.Diagnostics.CodeAnalysis;
using System.Diagnostics.Contracts;
using System.Linq;
using System.Numerics;
using System.Reactive.Linq;
using System.Runtime.Versioning;
+2 -1
View File
@@ -1,7 +1,7 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>net7.0</TargetFramework>
<TargetFramework>net6.0</TargetFramework>
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
<Platforms>x64</Platforms>
<PlatformTarget>x64</PlatformTarget>
@@ -15,6 +15,7 @@
<PackageReference Include="Google.Protobuf" Version="3.21.4" />
<PackageReference Include="System.Reactive" Version="5.0.0" />
<PackageReference Include="protobuf-net" Version="3.1.17" />
<PackageReference Include="System.Runtime.Experimental" Version="6.0.2" />
</ItemGroup>
<ItemGroup>
@@ -4,7 +4,6 @@ using System;
using System.Collections.Generic;
using System.Diagnostics.CodeAnalysis;
using System.Linq;
using System.Numerics;
namespace mbts.utils {
static class ExceptionAssert {
Loaded 100 of 430 files, more files were not shown because too many files have changed in this diff. Show more