chore: import upstream snapshot with attribution
This commit is contained in:
Vendored
+30
@@ -0,0 +1,30 @@
|
||||
##############################################################################
|
||||
##
|
||||
## Makefile for Detours.
|
||||
##
|
||||
## Microsoft Research Detours Package
|
||||
##
|
||||
## Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
##
|
||||
|
||||
ROOT = .
|
||||
!include "$(ROOT)\system.mak"
|
||||
|
||||
all:
|
||||
cd "$(MAKEDIR)\src"
|
||||
@$(MAKE) /NOLOGO /$(MAKEFLAGS)
|
||||
|
||||
clean:
|
||||
cd "$(MAKEDIR)\src"
|
||||
@$(MAKE) /NOLOGO /$(MAKEFLAGS) clean
|
||||
|
||||
realclean: clean
|
||||
cd "$(MAKEDIR)\src"
|
||||
@$(MAKE) /NOLOGO /$(MAKEFLAGS) realclean
|
||||
|
||||
-rmdir /q /s $(BINDS) 2> nul
|
||||
-rmdir /q /s dist 2> nul
|
||||
|
||||
-del /q /f /s *~ 2>nul
|
||||
|
||||
################################################################# End of File.
|
||||
Vendored
+74
@@ -0,0 +1,74 @@
|
||||
##############################################################################
|
||||
##
|
||||
## Makefile for Detours.
|
||||
##
|
||||
## Microsoft Research Detours Package, Version 4.0.1
|
||||
##
|
||||
## Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
##
|
||||
|
||||
#DETOURS_DEBUG="debug"
|
||||
|
||||
DETOURS_NAME=detours-$(DETOURS_TARGET_PROCESSOR)$(DETOURS_CONFIG)
|
||||
ROOT = ..
|
||||
!include "$(ROOT)\system.mak"
|
||||
|
||||
#######################/#######################################################
|
||||
##
|
||||
CFLAGS=/nologo /W4 /WX /we4777 /we4800 /Zi /MT /Gy /Gm- /Zl /Od /DDETOUR_DEBUG=$(DETOURS_DEBUG)
|
||||
|
||||
CFLAGS=$(CFLAGS) /DWIN32_LEAN_AND_MEAN /D_WIN32_WINNT=0x0601 $(DETOURS_DEFINITION)
|
||||
|
||||
!if defined(DETOURS_ANALYZE)
|
||||
CFLAGS=$(CFLAGS) /analyze
|
||||
!endif
|
||||
|
||||
OBJS = \
|
||||
$(OBJD)\detours.obj \
|
||||
$(OBJD)\disasm.obj \
|
||||
|
||||
##############################################################################
|
||||
##
|
||||
.SUFFIXES: .cpp .h .obj
|
||||
|
||||
!ifdef DETOURS_ANALYZE
|
||||
.cpp{$(OBJD)}.obj:
|
||||
$(CC) $(CFLAGS) /Fd$(BIND)\$(DETOURS_NAME).pdb /Fo$(OBJD)\ /c $<
|
||||
!else
|
||||
.cpp{$(OBJD)}.obj::
|
||||
$(CC) $(CFLAGS) /Fd$(BIND)\$(DETOURS_NAME).pdb /Fo$(OBJD)\ /c $<
|
||||
!endif
|
||||
|
||||
##############################################################################
|
||||
|
||||
all: dirs \
|
||||
$(BIND)\$(DETOURS_NAME).lib \
|
||||
$(BIND)\detours.h \
|
||||
|
||||
##############################################################################
|
||||
|
||||
clean:
|
||||
-del *~ 2>nul
|
||||
-del $(BIND)\$(DETOURS_NAME).pdb $(BIND)\$(DETOURS_NAME).pdb 2>nul
|
||||
-rmdir /q /s $(OBJD) 2>nul
|
||||
|
||||
realclean: clean
|
||||
-rmdir /q /s $(OBJDS) 2>nul
|
||||
|
||||
##############################################################################
|
||||
|
||||
dirs:
|
||||
@if not exist "$(BIND)" mkdir "$(BIND)" && echo. Created $(BIND)
|
||||
@if not exist "$(OBJD)" mkdir "$(OBJD)" && echo. Created $(OBJD)
|
||||
|
||||
$(BIND)\$(DETOURS_NAME).lib : $(OBJS)
|
||||
link /lib /MACHINE:$(DETOURS_TARGET_PROCESSOR) /out:$@ /nologo $(OBJS)
|
||||
|
||||
$(BIND)\detours.h : detours.h
|
||||
copy detours.h $@
|
||||
|
||||
$(OBJD)\detours.obj : detours.cpp detours.h
|
||||
$(OBJD)\disasm.obj : disasm.cpp detours.h
|
||||
|
||||
|
||||
################################################################# End of File.
|
||||
Vendored
+2388
File diff suppressed because it is too large
Load Diff
Vendored
+736
@@ -0,0 +1,736 @@
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// Core Detours Functionality (detours.h of detours.lib)
|
||||
//
|
||||
// Microsoft Research Detours Package, Version 4.0.1
|
||||
//
|
||||
// Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
//
|
||||
|
||||
#pragma once
|
||||
#ifndef _DETOURS_H_
|
||||
#define _DETOURS_H_
|
||||
|
||||
#define DETOURS_VERSION 0x4c0c1 // 0xMAJORcMINORcPATCH
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
|
||||
#ifdef DETOURS_INTERNAL
|
||||
|
||||
#define _CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS 1
|
||||
#define _ARM_WINAPI_PARTITION_DESKTOP_SDK_AVAILABLE 1
|
||||
|
||||
#pragma warning(disable:4068) // unknown pragma (suppress)
|
||||
|
||||
#if _MSC_VER >= 1900
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4091) // empty typedef
|
||||
#endif
|
||||
|
||||
// Suppress declspec(dllimport) for the sake of Detours
|
||||
// users that provide kernel32 functionality themselves.
|
||||
// This is ok in the mainstream case, it will just cost
|
||||
// an extra instruction calling some functions, which
|
||||
// LTCG optimizes away.
|
||||
//
|
||||
#define _KERNEL32_ 1
|
||||
#define _USER32_ 1
|
||||
|
||||
#include <windows.h>
|
||||
#if (_MSC_VER < 1310)
|
||||
#else
|
||||
#pragma warning(push)
|
||||
#if _MSC_VER > 1400
|
||||
#pragma warning(disable:6102 6103) // /analyze warnings
|
||||
#endif
|
||||
#include <strsafe.h>
|
||||
#include <intsafe.h>
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
#include <crtdbg.h>
|
||||
|
||||
// Allow Detours to cleanly compile with the MingW toolchain.
|
||||
//
|
||||
#ifdef __GNUC__
|
||||
#define __try
|
||||
#define __except(x) if (0)
|
||||
#include <strsafe.h>
|
||||
#include <intsafe.h>
|
||||
#endif
|
||||
|
||||
// From winerror.h, as this error isn't found in some SDKs:
|
||||
//
|
||||
// MessageId: ERROR_DYNAMIC_CODE_BLOCKED
|
||||
//
|
||||
// MessageText:
|
||||
//
|
||||
// The operation was blocked as the process prohibits dynamic code generation.
|
||||
//
|
||||
#define ERROR_DYNAMIC_CODE_BLOCKED 1655L
|
||||
|
||||
#endif // DETOURS_INTERNAL
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
|
||||
#undef DETOURS_X64
|
||||
#undef DETOURS_X86
|
||||
#undef DETOURS_IA64
|
||||
#undef DETOURS_ARM
|
||||
#undef DETOURS_ARM64
|
||||
#undef DETOURS_BITS
|
||||
#undef DETOURS_32BIT
|
||||
#undef DETOURS_64BIT
|
||||
|
||||
#if defined(_X86_)
|
||||
#define DETOURS_X86
|
||||
#define DETOURS_OPTION_BITS 64
|
||||
|
||||
#elif defined(_AMD64_)
|
||||
#define DETOURS_X64
|
||||
#define DETOURS_OPTION_BITS 32
|
||||
|
||||
#elif defined(_IA64_)
|
||||
#define DETOURS_IA64
|
||||
#define DETOURS_OPTION_BITS 32
|
||||
|
||||
#elif defined(_ARM_)
|
||||
#define DETOURS_ARM
|
||||
|
||||
#elif defined(_ARM64_)
|
||||
#define DETOURS_ARM64
|
||||
|
||||
#else
|
||||
#error Unknown architecture (x86, amd64, ia64, arm, arm64)
|
||||
#endif
|
||||
|
||||
#ifdef _WIN64
|
||||
#undef DETOURS_32BIT
|
||||
#define DETOURS_64BIT 1
|
||||
#define DETOURS_BITS 64
|
||||
// If all 64bit kernels can run one and only one 32bit architecture.
|
||||
//#define DETOURS_OPTION_BITS 32
|
||||
#else
|
||||
#define DETOURS_32BIT 1
|
||||
#undef DETOURS_64BIT
|
||||
#define DETOURS_BITS 32
|
||||
// If all 64bit kernels can run one and only one 32bit architecture.
|
||||
//#define DETOURS_OPTION_BITS 32
|
||||
#endif
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
|
||||
#if (_MSC_VER < 1299) && !defined(__MINGW32__)
|
||||
typedef LONG LONG_PTR;
|
||||
typedef ULONG ULONG_PTR;
|
||||
#endif
|
||||
|
||||
///////////////////////////////////////////////// SAL 2.0 Annotations w/o SAL.
|
||||
//
|
||||
// These definitions are include so that Detours will build even if the
|
||||
// compiler doesn't have full SAL 2.0 support.
|
||||
//
|
||||
#ifndef DETOURS_DONT_REMOVE_SAL_20
|
||||
|
||||
#ifdef DETOURS_TEST_REMOVE_SAL_20
|
||||
#undef _Analysis_assume_
|
||||
#undef _Benign_race_begin_
|
||||
#undef _Benign_race_end_
|
||||
#undef _Field_range_
|
||||
#undef _Field_size_
|
||||
#undef _In_
|
||||
#undef _In_bytecount_
|
||||
#undef _In_count_
|
||||
#undef __in_ecount
|
||||
#undef _In_opt_
|
||||
#undef _In_opt_bytecount_
|
||||
#undef _In_opt_count_
|
||||
#undef _In_opt_z_
|
||||
#undef _In_range_
|
||||
#undef _In_reads_
|
||||
#undef _In_reads_bytes_
|
||||
#undef _In_reads_opt_
|
||||
#undef _In_reads_opt_bytes_
|
||||
#undef _In_reads_or_z_
|
||||
#undef _In_z_
|
||||
#undef _Inout_
|
||||
#undef _Inout_opt_
|
||||
#undef _Inout_z_count_
|
||||
#undef _Out_
|
||||
#undef _Out_opt_
|
||||
#undef _Out_writes_
|
||||
#undef _Outptr_result_maybenull_
|
||||
#undef _Readable_bytes_
|
||||
#undef _Success_
|
||||
#undef _Writable_bytes_
|
||||
#undef _Pre_notnull_
|
||||
#endif
|
||||
|
||||
#if defined(_Deref_out_opt_z_) && !defined(_Outptr_result_maybenull_)
|
||||
#define _Outptr_result_maybenull_ _Deref_out_opt_z_
|
||||
#endif
|
||||
|
||||
#if defined(_In_count_) && !defined(_In_reads_)
|
||||
#define _In_reads_(x) _In_count_(x)
|
||||
#endif
|
||||
|
||||
#if defined(_In_opt_count_) && !defined(_In_reads_opt_)
|
||||
#define _In_reads_opt_(x) _In_opt_count_(x)
|
||||
#endif
|
||||
|
||||
#if defined(_In_opt_bytecount_) && !defined(_In_reads_opt_bytes_)
|
||||
#define _In_reads_opt_bytes_(x) _In_opt_bytecount_(x)
|
||||
#endif
|
||||
|
||||
#if defined(_In_bytecount_) && !defined(_In_reads_bytes_)
|
||||
#define _In_reads_bytes_(x) _In_bytecount_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _In_
|
||||
#define _In_
|
||||
#endif
|
||||
|
||||
#ifndef _In_bytecount_
|
||||
#define _In_bytecount_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _In_count_
|
||||
#define _In_count_(x)
|
||||
#endif
|
||||
|
||||
#ifndef __in_ecount
|
||||
#define __in_ecount(x)
|
||||
#endif
|
||||
|
||||
#ifndef _In_opt_
|
||||
#define _In_opt_
|
||||
#endif
|
||||
|
||||
#ifndef _In_opt_bytecount_
|
||||
#define _In_opt_bytecount_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _In_opt_count_
|
||||
#define _In_opt_count_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _In_opt_z_
|
||||
#define _In_opt_z_
|
||||
#endif
|
||||
|
||||
#ifndef _In_range_
|
||||
#define _In_range_(x,y)
|
||||
#endif
|
||||
|
||||
#ifndef _In_reads_
|
||||
#define _In_reads_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _In_reads_bytes_
|
||||
#define _In_reads_bytes_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _In_reads_opt_
|
||||
#define _In_reads_opt_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _In_reads_opt_bytes_
|
||||
#define _In_reads_opt_bytes_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _In_reads_or_z_
|
||||
#define _In_reads_or_z_
|
||||
#endif
|
||||
|
||||
#ifndef _In_z_
|
||||
#define _In_z_
|
||||
#endif
|
||||
|
||||
#ifndef _Inout_
|
||||
#define _Inout_
|
||||
#endif
|
||||
|
||||
#ifndef _Inout_opt_
|
||||
#define _Inout_opt_
|
||||
#endif
|
||||
|
||||
#ifndef _Inout_z_count_
|
||||
#define _Inout_z_count_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _Out_
|
||||
#define _Out_
|
||||
#endif
|
||||
|
||||
#ifndef _Out_opt_
|
||||
#define _Out_opt_
|
||||
#endif
|
||||
|
||||
#ifndef _Out_writes_
|
||||
#define _Out_writes_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _Outptr_result_maybenull_
|
||||
#define _Outptr_result_maybenull_
|
||||
#endif
|
||||
|
||||
#ifndef _Writable_bytes_
|
||||
#define _Writable_bytes_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _Readable_bytes_
|
||||
#define _Readable_bytes_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _Success_
|
||||
#define _Success_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _Pre_notnull_
|
||||
#define _Pre_notnull_
|
||||
#endif
|
||||
|
||||
#ifdef DETOURS_INTERNAL
|
||||
|
||||
#pragma warning(disable:4615) // unknown warning type (suppress with older compilers)
|
||||
|
||||
#ifndef _Benign_race_begin_
|
||||
#define _Benign_race_begin_
|
||||
#endif
|
||||
|
||||
#ifndef _Benign_race_end_
|
||||
#define _Benign_race_end_
|
||||
#endif
|
||||
|
||||
#ifndef _Field_size_
|
||||
#define _Field_size_(x)
|
||||
#endif
|
||||
|
||||
#ifndef _Field_range_
|
||||
#define _Field_range_(x,y)
|
||||
#endif
|
||||
|
||||
#ifndef _Analysis_assume_
|
||||
#define _Analysis_assume_(x)
|
||||
#endif
|
||||
|
||||
#endif // DETOURS_INTERNAL
|
||||
#endif // DETOURS_DONT_REMOVE_SAL_20
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
#ifndef GUID_DEFINED
|
||||
#define GUID_DEFINED
|
||||
typedef struct _GUID
|
||||
{
|
||||
DWORD Data1;
|
||||
WORD Data2;
|
||||
WORD Data3;
|
||||
BYTE Data4[ 8 ];
|
||||
} GUID;
|
||||
|
||||
#ifdef INITGUID
|
||||
#define DEFINE_GUID(name, l, w1, w2, b1, b2, b3, b4, b5, b6, b7, b8) \
|
||||
const GUID name \
|
||||
= { l, w1, w2, { b1, b2, b3, b4, b5, b6, b7, b8 } }
|
||||
#else
|
||||
#define DEFINE_GUID(name, l, w1, w2, b1, b2, b3, b4, b5, b6, b7, b8) \
|
||||
const GUID name
|
||||
#endif // INITGUID
|
||||
#endif // !GUID_DEFINED
|
||||
|
||||
#if defined(__cplusplus)
|
||||
#ifndef _REFGUID_DEFINED
|
||||
#define _REFGUID_DEFINED
|
||||
#define REFGUID const GUID &
|
||||
#endif // !_REFGUID_DEFINED
|
||||
#else // !__cplusplus
|
||||
#ifndef _REFGUID_DEFINED
|
||||
#define _REFGUID_DEFINED
|
||||
#define REFGUID const GUID * const
|
||||
#endif // !_REFGUID_DEFINED
|
||||
#endif // !__cplusplus
|
||||
|
||||
#ifndef ARRAYSIZE
|
||||
#define ARRAYSIZE(x) (sizeof(x)/sizeof(x[0]))
|
||||
#endif
|
||||
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif // __cplusplus
|
||||
|
||||
/////////////////////////////////////////////////// Instruction Target Macros.
|
||||
//
|
||||
#define DETOUR_INSTRUCTION_TARGET_NONE ((PVOID)0)
|
||||
#define DETOUR_INSTRUCTION_TARGET_DYNAMIC ((PVOID)(LONG_PTR)-1)
|
||||
#define DETOUR_SECTION_HEADER_SIGNATURE 0x00727444 // "Dtr\0"
|
||||
|
||||
extern const GUID DETOUR_EXE_RESTORE_GUID;
|
||||
extern const GUID DETOUR_EXE_HELPER_GUID;
|
||||
|
||||
#define DETOUR_TRAMPOLINE_SIGNATURE 0x21727444 // Dtr!
|
||||
typedef struct _DETOUR_TRAMPOLINE DETOUR_TRAMPOLINE, *PDETOUR_TRAMPOLINE;
|
||||
|
||||
#ifndef DETOUR_MAX_SUPPORTED_IMAGE_SECTION_HEADERS
|
||||
#define DETOUR_MAX_SUPPORTED_IMAGE_SECTION_HEADERS 32
|
||||
#endif // !DETOUR_MAX_SUPPORTED_IMAGE_SECTION_HEADERS
|
||||
/*
|
||||
///////////////////////////////////////////////////////////// Binary Typedefs.
|
||||
//
|
||||
typedef BOOL (CALLBACK *PF_DETOUR_BINARY_BYWAY_CALLBACK)(
|
||||
_In_opt_ PVOID pContext,
|
||||
_In_opt_ LPCSTR pszFile,
|
||||
_Outptr_result_maybenull_ LPCSTR *ppszOutFile);
|
||||
|
||||
typedef BOOL (CALLBACK *PF_DETOUR_BINARY_FILE_CALLBACK)(
|
||||
_In_opt_ PVOID pContext,
|
||||
_In_ LPCSTR pszOrigFile,
|
||||
_In_ LPCSTR pszFile,
|
||||
_Outptr_result_maybenull_ LPCSTR *ppszOutFile);
|
||||
|
||||
typedef BOOL (CALLBACK *PF_DETOUR_BINARY_SYMBOL_CALLBACK)(
|
||||
_In_opt_ PVOID pContext,
|
||||
_In_ ULONG nOrigOrdinal,
|
||||
_In_ ULONG nOrdinal,
|
||||
_Out_ ULONG *pnOutOrdinal,
|
||||
_In_opt_ LPCSTR pszOrigSymbol,
|
||||
_In_opt_ LPCSTR pszSymbol,
|
||||
_Outptr_result_maybenull_ LPCSTR *ppszOutSymbol);
|
||||
|
||||
typedef BOOL (CALLBACK *PF_DETOUR_BINARY_COMMIT_CALLBACK)(
|
||||
_In_opt_ PVOID pContext);
|
||||
|
||||
typedef BOOL (CALLBACK *PF_DETOUR_ENUMERATE_EXPORT_CALLBACK)(_In_opt_ PVOID pContext,
|
||||
_In_ ULONG nOrdinal,
|
||||
_In_opt_ LPCSTR pszName,
|
||||
_In_opt_ PVOID pCode);
|
||||
|
||||
typedef BOOL (CALLBACK *PF_DETOUR_IMPORT_FILE_CALLBACK)(_In_opt_ PVOID pContext,
|
||||
_In_opt_ HMODULE hModule,
|
||||
_In_opt_ LPCSTR pszFile);
|
||||
|
||||
typedef BOOL (CALLBACK *PF_DETOUR_IMPORT_FUNC_CALLBACK)(_In_opt_ PVOID pContext,
|
||||
_In_ DWORD nOrdinal,
|
||||
_In_opt_ LPCSTR pszFunc,
|
||||
_In_opt_ PVOID pvFunc);
|
||||
|
||||
// Same as PF_DETOUR_IMPORT_FUNC_CALLBACK but extra indirection on last parameter.
|
||||
typedef BOOL (CALLBACK *PF_DETOUR_IMPORT_FUNC_CALLBACK_EX)(_In_opt_ PVOID pContext,
|
||||
_In_ DWORD nOrdinal,
|
||||
_In_opt_ LPCSTR pszFunc,
|
||||
_In_opt_ PVOID* ppvFunc);
|
||||
*/
|
||||
typedef VOID * PDETOUR_BINARY;
|
||||
typedef VOID * PDETOUR_LOADED_BINARY;
|
||||
|
||||
//////////////////////////////////////////////////////////// Transaction APIs.
|
||||
//
|
||||
LONG WINAPI DetourTransactionBegin(VOID);
|
||||
LONG WINAPI DetourTransactionAbort(VOID);
|
||||
LONG WINAPI DetourTransactionCommit(VOID);
|
||||
LONG WINAPI DetourTransactionCommitEx(_Out_opt_ PVOID **pppFailedPointer);
|
||||
|
||||
LONG WINAPI DetourUpdateThread(_In_ HANDLE hThread);
|
||||
|
||||
LONG WINAPI DetourAttach(_Inout_ PVOID *ppPointer,
|
||||
_In_ PVOID pDetour);
|
||||
|
||||
LONG WINAPI DetourAttachEx(_Inout_ PVOID *ppPointer,
|
||||
_In_ PVOID pDetour,
|
||||
_Out_opt_ PDETOUR_TRAMPOLINE *ppRealTrampoline,
|
||||
_Out_opt_ PVOID *ppRealTarget,
|
||||
_Out_opt_ PVOID *ppRealDetour);
|
||||
|
||||
LONG WINAPI DetourDetach(_Inout_ PVOID *ppPointer,
|
||||
_In_ PVOID pDetour);
|
||||
|
||||
BOOL WINAPI DetourSetIgnoreTooSmall(_In_ BOOL fIgnore);
|
||||
BOOL WINAPI DetourSetRetainRegions(_In_ BOOL fRetain);
|
||||
PVOID WINAPI DetourSetSystemRegionLowerBound(_In_ PVOID pSystemRegionLowerBound);
|
||||
PVOID WINAPI DetourSetSystemRegionUpperBound(_In_ PVOID pSystemRegionUpperBound);
|
||||
|
||||
////////////////////////////////////////////////////////////// Code Functions.
|
||||
//
|
||||
PVOID WINAPI DetourFindFunction(_In_ LPCWSTR pszModule,
|
||||
_In_ LPCSTR pszFunction);
|
||||
PVOID WINAPI DetourCodeFromPointer(_In_ PVOID pPointer,
|
||||
_Out_opt_ PVOID *ppGlobals);
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif // __cplusplus
|
||||
PVOID WINAPI DetourCopyInstruction(_In_opt_ PVOID pDst,
|
||||
_Inout_opt_ PVOID *ppDstPool,
|
||||
_In_ PVOID pSrc,
|
||||
_Out_opt_ PVOID *ppTarget,
|
||||
_Out_opt_ LONG *plExtra);
|
||||
BOOL WINAPI DetourSetCodeModule(_In_ HMODULE hModule,
|
||||
_In_ BOOL fLimitReferencesToModule);
|
||||
PVOID WINAPI DetourAllocateRegionWithinJumpBounds(_In_ LPCVOID pbTarget,
|
||||
_Out_ PDWORD pcbAllocatedSize);
|
||||
BOOL WINAPI DetourIsFunctionImported(_In_ PBYTE pbCode,
|
||||
_In_ PBYTE pbAddress);
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif // __cplusplus
|
||||
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif // __cplusplus
|
||||
|
||||
/////////////////////////////////////////////////// Type-safe overloads for C++
|
||||
//
|
||||
#if __cplusplus >= 201103L || _MSVC_LANG >= 201103L
|
||||
#include <type_traits>
|
||||
|
||||
template<typename T>
|
||||
struct DetoursIsFunctionPointer : std::false_type {};
|
||||
|
||||
template<typename T>
|
||||
struct DetoursIsFunctionPointer<T*> : std::is_function<typename std::remove_pointer<T>::type> {};
|
||||
|
||||
template<
|
||||
typename T,
|
||||
typename std::enable_if<DetoursIsFunctionPointer<T>::value, int>::type = 0>
|
||||
LONG DetourAttach(_Inout_ T *ppPointer,
|
||||
_In_ T pDetour) noexcept
|
||||
{
|
||||
return DetourAttach(
|
||||
reinterpret_cast<void**>(ppPointer),
|
||||
reinterpret_cast<void*>(pDetour));
|
||||
}
|
||||
|
||||
template<
|
||||
typename T,
|
||||
typename std::enable_if<DetoursIsFunctionPointer<T>::value, int>::type = 0>
|
||||
LONG DetourAttachEx(_Inout_ T *ppPointer,
|
||||
_In_ T pDetour,
|
||||
_Out_opt_ PDETOUR_TRAMPOLINE *ppRealTrampoline,
|
||||
_Out_opt_ T *ppRealTarget,
|
||||
_Out_opt_ T *ppRealDetour) noexcept
|
||||
{
|
||||
return DetourAttachEx(
|
||||
reinterpret_cast<void**>(ppPointer),
|
||||
reinterpret_cast<void*>(pDetour),
|
||||
ppRealTrampoline,
|
||||
reinterpret_cast<void**>(ppRealTarget),
|
||||
reinterpret_cast<void**>(ppRealDetour));
|
||||
}
|
||||
|
||||
template<
|
||||
typename T,
|
||||
typename std::enable_if<DetoursIsFunctionPointer<T>::value, int>::type = 0>
|
||||
LONG DetourDetach(_Inout_ T *ppPointer,
|
||||
_In_ T pDetour) noexcept
|
||||
{
|
||||
return DetourDetach(
|
||||
reinterpret_cast<void**>(ppPointer),
|
||||
reinterpret_cast<void*>(pDetour));
|
||||
}
|
||||
|
||||
#endif // __cplusplus >= 201103L || _MSVC_LANG >= 201103L
|
||||
//
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
//////////////////////////////////////////////// Detours Internal Definitions.
|
||||
//
|
||||
#ifdef __cplusplus
|
||||
#ifdef DETOURS_INTERNAL
|
||||
|
||||
#define NOTHROW
|
||||
// #define NOTHROW (nothrow)
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
#if (_MSC_VER < 1299) && !defined(__GNUC__)
|
||||
#include <imagehlp.h>
|
||||
typedef IMAGEHLP_MODULE IMAGEHLP_MODULE64;
|
||||
typedef PIMAGEHLP_MODULE PIMAGEHLP_MODULE64;
|
||||
typedef IMAGEHLP_SYMBOL SYMBOL_INFO;
|
||||
typedef PIMAGEHLP_SYMBOL PSYMBOL_INFO;
|
||||
|
||||
static inline
|
||||
LONG InterlockedCompareExchange(_Inout_ LONG *ptr, _In_ LONG nval, _In_ LONG oval)
|
||||
{
|
||||
return (LONG)::InterlockedCompareExchange((PVOID*)ptr, (PVOID)nval, (PVOID)oval);
|
||||
}
|
||||
#else
|
||||
#pragma warning(push)
|
||||
#pragma warning(disable:4091) // empty typedef
|
||||
#include <dbghelp.h>
|
||||
#pragma warning(pop)
|
||||
#endif
|
||||
|
||||
#if defined(_INC_STDIO) && !defined(_CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS)
|
||||
#error detours.h must be included before stdio.h (or at least define _CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS earlier)
|
||||
#endif
|
||||
#define _CRT_STDIO_ARBITRARY_WIDE_SPECIFIERS 1
|
||||
|
||||
|
||||
#if 1 || defined(DETOURS_IA64)
|
||||
|
||||
//
|
||||
// IA64 instructions are 41 bits, 3 per bundle, plus 5 bit bundle template => 128 bits per bundle.
|
||||
//
|
||||
|
||||
#define DETOUR_IA64_INSTRUCTIONS_PER_BUNDLE (3)
|
||||
|
||||
#define DETOUR_IA64_TEMPLATE_OFFSET (0)
|
||||
#define DETOUR_IA64_TEMPLATE_SIZE (5)
|
||||
|
||||
#define DETOUR_IA64_INSTRUCTION_SIZE (41)
|
||||
#define DETOUR_IA64_INSTRUCTION0_OFFSET (DETOUR_IA64_TEMPLATE_SIZE)
|
||||
#define DETOUR_IA64_INSTRUCTION1_OFFSET (DETOUR_IA64_TEMPLATE_SIZE + DETOUR_IA64_INSTRUCTION_SIZE)
|
||||
#define DETOUR_IA64_INSTRUCTION2_OFFSET (DETOUR_IA64_TEMPLATE_SIZE + DETOUR_IA64_INSTRUCTION_SIZE + DETOUR_IA64_INSTRUCTION_SIZE)
|
||||
|
||||
C_ASSERT(DETOUR_IA64_TEMPLATE_SIZE + DETOUR_IA64_INSTRUCTIONS_PER_BUNDLE * DETOUR_IA64_INSTRUCTION_SIZE == 128);
|
||||
|
||||
__declspec(align(16)) struct DETOUR_IA64_BUNDLE
|
||||
{
|
||||
public:
|
||||
union
|
||||
{
|
||||
BYTE data[16];
|
||||
UINT64 wide[2];
|
||||
};
|
||||
|
||||
enum {
|
||||
A_UNIT = 1u,
|
||||
I_UNIT = 2u,
|
||||
M_UNIT = 3u,
|
||||
B_UNIT = 4u,
|
||||
F_UNIT = 5u,
|
||||
L_UNIT = 6u,
|
||||
X_UNIT = 7u,
|
||||
};
|
||||
struct DETOUR_IA64_METADATA
|
||||
{
|
||||
ULONG nTemplate : 8; // Instruction template.
|
||||
ULONG nUnit0 : 4; // Unit for slot 0
|
||||
ULONG nUnit1 : 4; // Unit for slot 1
|
||||
ULONG nUnit2 : 4; // Unit for slot 2
|
||||
};
|
||||
|
||||
protected:
|
||||
static const DETOUR_IA64_METADATA s_rceCopyTable[33];
|
||||
|
||||
UINT RelocateBundle(_Inout_ DETOUR_IA64_BUNDLE* pDst, _Inout_opt_ DETOUR_IA64_BUNDLE* pBundleExtra) const;
|
||||
|
||||
bool RelocateInstruction(_Inout_ DETOUR_IA64_BUNDLE* pDst,
|
||||
_In_ BYTE slot,
|
||||
_Inout_opt_ DETOUR_IA64_BUNDLE* pBundleExtra) const;
|
||||
|
||||
// 120 112 104 96 88 80 72 64 56 48 40 32 24 16 8 0
|
||||
// f. e. d. c. b. a. 9. 8. 7. 6. 5. 4. 3. 2. 1. 0.
|
||||
|
||||
// 00
|
||||
// f.e. d.c. b.a. 9.8. 7.6. 5.4. 3.2. 1.0.
|
||||
// 0000 0000 0000 0000 0000 0000 0000 001f : Template [4..0]
|
||||
// 0000 0000 0000 0000 0000 03ff ffff ffe0 : Zero [ 41.. 5]
|
||||
// 0000 0000 0000 0000 0000 3c00 0000 0000 : Zero [ 45.. 42]
|
||||
// 0000 0000 0007 ffff ffff c000 0000 0000 : One [ 82.. 46]
|
||||
// 0000 0000 0078 0000 0000 0000 0000 0000 : One [ 86.. 83]
|
||||
// 0fff ffff ff80 0000 0000 0000 0000 0000 : Two [123.. 87]
|
||||
// f000 0000 0000 0000 0000 0000 0000 0000 : Two [127..124]
|
||||
BYTE GetTemplate() const;
|
||||
// Get 4 bit opcodes.
|
||||
BYTE GetInst0() const;
|
||||
BYTE GetInst1() const;
|
||||
BYTE GetInst2() const;
|
||||
BYTE GetUnit(BYTE slot) const;
|
||||
BYTE GetUnit0() const;
|
||||
BYTE GetUnit1() const;
|
||||
BYTE GetUnit2() const;
|
||||
// Get 37 bit data.
|
||||
UINT64 GetData0() const;
|
||||
UINT64 GetData1() const;
|
||||
UINT64 GetData2() const;
|
||||
|
||||
// Get/set the full 41 bit instructions.
|
||||
UINT64 GetInstruction(BYTE slot) const;
|
||||
UINT64 GetInstruction0() const;
|
||||
UINT64 GetInstruction1() const;
|
||||
UINT64 GetInstruction2() const;
|
||||
void SetInstruction(BYTE slot, UINT64 instruction);
|
||||
void SetInstruction0(UINT64 instruction);
|
||||
void SetInstruction1(UINT64 instruction);
|
||||
void SetInstruction2(UINT64 instruction);
|
||||
|
||||
// Get/set bitfields.
|
||||
static UINT64 GetBits(UINT64 Value, UINT64 Offset, UINT64 Count);
|
||||
static UINT64 SetBits(UINT64 Value, UINT64 Offset, UINT64 Count, UINT64 Field);
|
||||
|
||||
// Get specific read-only fields.
|
||||
static UINT64 GetOpcode(UINT64 instruction); // 4bit opcode
|
||||
static UINT64 GetX(UINT64 instruction); // 1bit opcode extension
|
||||
static UINT64 GetX3(UINT64 instruction); // 3bit opcode extension
|
||||
static UINT64 GetX6(UINT64 instruction); // 6bit opcode extension
|
||||
|
||||
// Get/set specific fields.
|
||||
static UINT64 GetImm7a(UINT64 instruction);
|
||||
static UINT64 SetImm7a(UINT64 instruction, UINT64 imm7a);
|
||||
static UINT64 GetImm13c(UINT64 instruction);
|
||||
static UINT64 SetImm13c(UINT64 instruction, UINT64 imm13c);
|
||||
static UINT64 GetSignBit(UINT64 instruction);
|
||||
static UINT64 SetSignBit(UINT64 instruction, UINT64 signBit);
|
||||
static UINT64 GetImm20a(UINT64 instruction);
|
||||
static UINT64 SetImm20a(UINT64 instruction, UINT64 imm20a);
|
||||
static UINT64 GetImm20b(UINT64 instruction);
|
||||
static UINT64 SetImm20b(UINT64 instruction, UINT64 imm20b);
|
||||
|
||||
static UINT64 SignExtend(UINT64 Value, UINT64 Offset);
|
||||
|
||||
BOOL IsMovlGp() const;
|
||||
|
||||
VOID SetInst(BYTE Slot, BYTE nInst);
|
||||
VOID SetInst0(BYTE nInst);
|
||||
VOID SetInst1(BYTE nInst);
|
||||
VOID SetInst2(BYTE nInst);
|
||||
VOID SetData(BYTE Slot, UINT64 nData);
|
||||
VOID SetData0(UINT64 nData);
|
||||
VOID SetData1(UINT64 nData);
|
||||
VOID SetData2(UINT64 nData);
|
||||
BOOL SetNop(BYTE Slot);
|
||||
BOOL SetNop0();
|
||||
BOOL SetNop1();
|
||||
BOOL SetNop2();
|
||||
|
||||
public:
|
||||
BOOL IsBrl() const;
|
||||
VOID SetBrl();
|
||||
VOID SetBrl(UINT64 target);
|
||||
UINT64 GetBrlTarget() const;
|
||||
VOID SetBrlTarget(UINT64 target);
|
||||
VOID SetBrlImm(UINT64 imm);
|
||||
UINT64 GetBrlImm() const;
|
||||
|
||||
UINT64 GetMovlGp() const;
|
||||
VOID SetMovlGp(UINT64 gp);
|
||||
|
||||
VOID SetStop();
|
||||
|
||||
UINT Copy(_Out_ DETOUR_IA64_BUNDLE *pDst, _Inout_opt_ DETOUR_IA64_BUNDLE* pBundleExtra = NULL) const;
|
||||
};
|
||||
#endif // DETOURS_IA64
|
||||
|
||||
#ifdef DETOURS_ARM
|
||||
|
||||
#define DETOURS_PFUNC_TO_PBYTE(p) ((PBYTE)(((ULONG_PTR)(p)) & ~(ULONG_PTR)1))
|
||||
#define DETOURS_PBYTE_TO_PFUNC(p) ((PBYTE)(((ULONG_PTR)(p)) | (ULONG_PTR)1))
|
||||
|
||||
#endif // DETOURS_ARM
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
#endif // DETOURS_INTERNAL
|
||||
#endif // __cplusplus
|
||||
|
||||
#endif // _DETOURS_H_
|
||||
//
|
||||
//////////////////////////////////////////////////////////////// End of File.
|
||||
Vendored
+4270
File diff suppressed because it is too large
Load Diff
Vendored
+112
@@ -0,0 +1,112 @@
|
||||
##############################################################################
|
||||
##
|
||||
## Establish build target type for Detours.
|
||||
##
|
||||
## Microsoft Research Detours Package
|
||||
##
|
||||
## Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
##
|
||||
|
||||
############################################## Determine Processor Build Type.
|
||||
#
|
||||
# Default the detours architecture to match the compiler target that
|
||||
# has been selected by the user via the VS Developer Command Prompt
|
||||
# they launched.
|
||||
|
||||
DETOURS_TARGET_PROCESSOR=arm64
|
||||
|
||||
DETOURS_DEFINITION=""
|
||||
|
||||
!IF "$(DETOURS_TARGET_PROCESSOR)" == "" && "$(VSCMD_ARG_TGT_ARCH)" != ""
|
||||
DETOURS_TARGET_PROCESSOR = $(VSCMD_ARG_TGT_ARCH)
|
||||
!ENDIF
|
||||
|
||||
!IF "$(DETOURS_TARGET_PROCESSOR)" == "" && "$(PROCESSOR_ARCHITEW6432)" != ""
|
||||
DETOURS_TARGET_PROCESSOR = x86
|
||||
!ENDIF
|
||||
|
||||
!IF "$(DETOURS_TARGET_PROCESSOR)" == ""
|
||||
DETOURS_TARGET_PROCESSOR = $(PROCESSOR_ARCHITECTURE)
|
||||
!ENDIF
|
||||
|
||||
# Uppercase DETOURS_TARGET_PROCESSOR
|
||||
DETOURS_TARGET_PROCESSOR=$(DETOURS_TARGET_PROCESSOR:A=a)
|
||||
DETOURS_TARGET_PROCESSOR=$(DETOURS_TARGET_PROCESSOR:D=d)
|
||||
DETOURS_TARGET_PROCESSOR=$(DETOURS_TARGET_PROCESSOR:I=i)
|
||||
DETOURS_TARGET_PROCESSOR=$(DETOURS_TARGET_PROCESSOR:M=m)
|
||||
DETOURS_TARGET_PROCESSOR=$(DETOURS_TARGET_PROCESSOR:R=r)
|
||||
DETOURS_TARGET_PROCESSOR=$(DETOURS_TARGET_PROCESSOR:X=x)
|
||||
|
||||
|
||||
!IF "$(DETOURS_TARGET_PROCESSOR)" == "amd64"
|
||||
DETOURS_TARGET_PROCESSOR = x64
|
||||
!ENDIF
|
||||
|
||||
|
||||
!if "$(DETOURS_TARGET_PROCESSOR:64=)" == "$(DETOURS_TARGET_PROCESSOR)"
|
||||
DETOURS_32BIT=1
|
||||
DETOURS_BITS=32
|
||||
!else
|
||||
DETOURS_64BIT=1
|
||||
DETOURS_BITS=64
|
||||
!endif
|
||||
|
||||
########################################## Configure build based on Processor.
|
||||
##
|
||||
## DETOURS_OPTION_PROCESSOR: Set this macro if the processor *will* run code
|
||||
## from another ISA (i.e. x86 on x64).
|
||||
##
|
||||
## DETOURS_OPTION_BITS: Set this macro if the processor *may* have
|
||||
## an alternative word size.
|
||||
##
|
||||
!IF "$(DETOURS_TARGET_PROCESSOR)" == "x64"
|
||||
#!MESSAGE Building for 64-bit x64.
|
||||
DETOURS_SOURCE_BROWSING = 0
|
||||
DETOURS_OPTION_PROCESSOR=x86
|
||||
DETOURS_OPTION_BITS=32
|
||||
DETOURS_DEFINITION=/DDETOURS_X64_OFFLINE_LIBRARY
|
||||
!ELSEIF "$(DETOURS_TARGET_PROCESSOR)" == "ia64"
|
||||
#!MESSAGE Building for 64-bit IA64.
|
||||
DETOURS_OPTION_PROCESSOR=x86
|
||||
DETOURS_OPTION_BITS=32
|
||||
DETOURS_DEFINITION=/DDETOURS_X86_OFFLINE_LIBRARY
|
||||
!ELSEIF "$(DETOURS_TARGET_PROCESSOR)" == "x86"
|
||||
#!MESSAGE Building for 32-bit x86.
|
||||
DETOURS_OPTION_BITS=64
|
||||
# Don't set DETOURS_OPTION_PROCESSOR for x64 because we don't *know* that
|
||||
# we'll run on a 64-bit machine.
|
||||
!ELSEIF "$(DETOURS_TARGET_PROCESSOR)" == "arm"
|
||||
#!MESSAGE Building for 32-bit ARM.
|
||||
DETOURS_DEFINITION=/DDETOURS_ARM_OFFLINE_LIBRARY
|
||||
!ELSEIF "$(DETOURS_TARGET_PROCESSOR)" == "arm64"
|
||||
#!MESSAGE Building for 64-bit ARM.
|
||||
DETOURS_DEFINITION=/DDETOURS_ARM64_OFFLINE_LIBRARY
|
||||
!ELSE
|
||||
!MESSAGE Note: To select the target processor architecture set either
|
||||
!MESSAGE PROCESSOR_ARCHITECTURE or DETOURS_TARGET_PROCESSOR.
|
||||
!MESSAGE
|
||||
!ERROR Unknown target processor: "$(DETOURS_TARGET_PROCESSOR)"
|
||||
!ENDIF
|
||||
|
||||
##############################################################################
|
||||
##
|
||||
!IF "$(DETOURS_CONFIG)" == "debug"
|
||||
DETOURS_DEBUG=1
|
||||
DETOURS_CONFIG="-debug"
|
||||
!ELSE
|
||||
DETOURS_DEBUG=0
|
||||
!ENDIF
|
||||
|
||||
BIND = $(ROOT)\bin
|
||||
OBJD = $(BIND)\obj\$(DETOURS_TARGET_PROCESSOR)$(DETOURS_CONFIG)
|
||||
|
||||
BINDS = \
|
||||
$(ROOT)\bin
|
||||
|
||||
OBJDS = \
|
||||
$(BIND)\obj\x86$(DETOURS_CONFIG) \
|
||||
$(BIND)\obj\x64$(DETOURS_CONFIG) \
|
||||
$(BIND)\obj\arm$(DETOURS_CONFIG) \
|
||||
$(BIND)\obj\arm64$(DETOURS_CONFIG) \
|
||||
|
||||
##############################################################################
|
||||
Vendored
+43
@@ -0,0 +1,43 @@
|
||||
|
||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio Version 16
|
||||
VisualStudioVersion = 16.0.29519.181
|
||||
MinimumVisualStudioVersion = 10.0.40219.1
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "Detours", "Detours.vcxproj", "{37489709-8054-4903-9C49-A79846049FC9}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
DebugMDd|ARM = DebugMDd|ARM
|
||||
DebugMDd|ARM64 = DebugMDd|ARM64
|
||||
DebugMDd|x64 = DebugMDd|x64
|
||||
DebugMDd|x86 = DebugMDd|x86
|
||||
ReleaseMD|ARM = ReleaseMD|ARM
|
||||
ReleaseMD|ARM64 = ReleaseMD|ARM64
|
||||
ReleaseMD|x64 = ReleaseMD|x64
|
||||
ReleaseMD|x86 = ReleaseMD|x86
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.DebugMDd|ARM.ActiveCfg = DebugMDd|ARM
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.DebugMDd|ARM.Build.0 = DebugMDd|ARM
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.DebugMDd|ARM64.ActiveCfg = DebugMDd|ARM64
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.DebugMDd|ARM64.Build.0 = DebugMDd|ARM64
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.DebugMDd|x64.ActiveCfg = DebugMDd|x64
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.DebugMDd|x64.Build.0 = DebugMDd|x64
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.DebugMDd|x86.ActiveCfg = DebugMDd|Win32
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.DebugMDd|x86.Build.0 = DebugMDd|Win32
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.ReleaseMD|ARM.ActiveCfg = ReleaseMD|ARM
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.ReleaseMD|ARM.Build.0 = ReleaseMD|ARM
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.ReleaseMD|ARM64.ActiveCfg = ReleaseMD|ARM64
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.ReleaseMD|ARM64.Build.0 = ReleaseMD|ARM64
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.ReleaseMD|x64.ActiveCfg = ReleaseMD|x64
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.ReleaseMD|x64.Build.0 = ReleaseMD|x64
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.ReleaseMD|x86.ActiveCfg = ReleaseMD|Win32
|
||||
{37489709-8054-4903-9C49-A79846049FC9}.ReleaseMD|x86.Build.0 = ReleaseMD|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
SolutionGuid = {1E71C644-7F30-4025-B1DF-6A4F07A2EDB3}
|
||||
EndGlobalSection
|
||||
EndGlobal
|
||||
+602
@@ -0,0 +1,602 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="DebugMDd|ARM">
|
||||
<Configuration>DebugMDd</Configuration>
|
||||
<Platform>ARM</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="DebugMDd|ARM64">
|
||||
<Configuration>DebugMDd</Configuration>
|
||||
<Platform>ARM64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="DebugMDd|Win32">
|
||||
<Configuration>DebugMDd</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="ReleaseMD|ARM">
|
||||
<Configuration>ReleaseMD</Configuration>
|
||||
<Platform>ARM</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="ReleaseMD|ARM64">
|
||||
<Configuration>ReleaseMD</Configuration>
|
||||
<Platform>ARM64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="ReleaseMD|Win32">
|
||||
<Configuration>ReleaseMD</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="DebugMDd|x64">
|
||||
<Configuration>DebugMDd</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="ReleaseMD|x64">
|
||||
<Configuration>ReleaseMD</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<VCProjectVersion>15.0</VCProjectVersion>
|
||||
<ProjectGuid>{37489709-8054-4903-9C49-A79846049FC9}</ProjectGuid>
|
||||
<Keyword>Win32Proj</Keyword>
|
||||
<RootNamespace>Detours</RootNamespace>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|Win32'" Label="Configuration">
|
||||
<ConfigurationType>Makefile</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|Win32'" Label="Configuration">
|
||||
<ConfigurationType>Makefile</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|x64'" Label="Configuration">
|
||||
<ConfigurationType>Makefile</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|ARM'" Label="Configuration">
|
||||
<ConfigurationType>Makefile</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|ARM64'" Label="Configuration">
|
||||
<ConfigurationType>Makefile</ConfigurationType>
|
||||
<UseDebugLibraries>true</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|x64'" Label="Configuration">
|
||||
<ConfigurationType>Makefile</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|ARM'" Label="Configuration">
|
||||
<ConfigurationType>Makefile</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|ARM64'" Label="Configuration">
|
||||
<ConfigurationType>Makefile</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v142</PlatformToolset>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="Shared">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='DebugMDd|Win32'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|Win32'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='DebugMDd|x64'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|ARM'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|ARM64'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|x64'">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|ARM'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|ARM64'" Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|x64'">
|
||||
<NMakeBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</NMakeBuildCommandLine>
|
||||
<NMakeReBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean
|
||||
nmake</NMakeReBuildCommandLine>
|
||||
<NMakeCleanCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean</NMakeCleanCommandLine>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|ARM'">
|
||||
<NMakeBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</NMakeBuildCommandLine>
|
||||
<NMakeReBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean
|
||||
nmake</NMakeReBuildCommandLine>
|
||||
<NMakeCleanCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean</NMakeCleanCommandLine>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|ARM64'">
|
||||
<NMakeBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</NMakeBuildCommandLine>
|
||||
<NMakeReBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean
|
||||
nmake</NMakeReBuildCommandLine>
|
||||
<NMakeCleanCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean</NMakeCleanCommandLine>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|x64'">
|
||||
<NMakeBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</NMakeBuildCommandLine>
|
||||
<NMakeReBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean
|
||||
nmake</NMakeReBuildCommandLine>
|
||||
<NMakeCleanCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean</NMakeCleanCommandLine>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|ARM'">
|
||||
<NMakeBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</NMakeBuildCommandLine>
|
||||
<NMakeReBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean
|
||||
nmake</NMakeReBuildCommandLine>
|
||||
<NMakeCleanCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean</NMakeCleanCommandLine>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|Win32'">
|
||||
<NMakeBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</NMakeBuildCommandLine>
|
||||
<NMakeReBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean
|
||||
nmake</NMakeReBuildCommandLine>
|
||||
<NMakeCleanCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean</NMakeCleanCommandLine>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|Win32'">
|
||||
<NMakeBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</NMakeBuildCommandLine>
|
||||
<NMakeReBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean
|
||||
nmake</NMakeReBuildCommandLine>
|
||||
<NMakeCleanCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean</NMakeCleanCommandLine>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|ARM64'">
|
||||
<NMakeBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</NMakeBuildCommandLine>
|
||||
<NMakeReBuildCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean
|
||||
nmake</NMakeReBuildCommandLine>
|
||||
<NMakeCleanCommandLine>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake clean</NMakeCleanCommandLine>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>WIN32;_DEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<TreatWarningAsError>true</TreatWarningAsError>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
<ProgramDataBaseFileName>$(OutputPath)$(TargetName).pdb</ProgramDataBaseFileName>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<PostBuildEvent />
|
||||
<PreBuildEvent>
|
||||
<Command>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</Command>
|
||||
</PreBuildEvent>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|x64'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>_DEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<TreatWarningAsError>true</TreatWarningAsError>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
<PrecompiledHeaderFile />
|
||||
<PrecompiledHeaderOutputFile />
|
||||
<ProgramDataBaseFileName>$(OutputPath)$(TargetName).pdb</ProgramDataBaseFileName>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<PostBuildEvent />
|
||||
<PreBuildEvent>
|
||||
<Command>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</Command>
|
||||
</PreBuildEvent>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|ARM'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>_DEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<TreatWarningAsError>true</TreatWarningAsError>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
<PrecompiledHeaderFile>
|
||||
</PrecompiledHeaderFile>
|
||||
<PrecompiledHeaderOutputFile>
|
||||
</PrecompiledHeaderOutputFile>
|
||||
<ProgramDataBaseFileName>$(OutputPath)$(TargetName).pdb</ProgramDataBaseFileName>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<PostBuildEvent />
|
||||
<PreBuildEvent>
|
||||
<Command>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</Command>
|
||||
</PreBuildEvent>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='DebugMDd|ARM64'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<Optimization>Disabled</Optimization>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>_DEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<TreatWarningAsError>true</TreatWarningAsError>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<DebugInformationFormat>ProgramDatabase</DebugInformationFormat>
|
||||
<PrecompiledHeaderFile>
|
||||
</PrecompiledHeaderFile>
|
||||
<PrecompiledHeaderOutputFile>
|
||||
</PrecompiledHeaderOutputFile>
|
||||
<ProgramDataBaseFileName>$(OutputPath)$(TargetName).pdb</ProgramDataBaseFileName>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<PostBuildEvent />
|
||||
<PreBuildEvent>
|
||||
<Command>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</Command>
|
||||
</PreBuildEvent>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<Optimization>MaxSpeed</Optimization>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<TreatWarningAsError>true</TreatWarningAsError>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<ProgramDataBaseFileName>$(OutputPath)$(TargetName).pdb</ProgramDataBaseFileName>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<PostBuildEvent />
|
||||
<PreBuildEvent>
|
||||
<Command>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</Command>
|
||||
</PreBuildEvent>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|x64'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<Optimization>MaxSpeed</Optimization>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>NDEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<TreatWarningAsError>true</TreatWarningAsError>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<PrecompiledHeaderFile />
|
||||
<PrecompiledHeaderOutputFile />
|
||||
<ProgramDataBaseFileName>$(OutputPath)$(TargetName).pdb</ProgramDataBaseFileName>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<PostBuildEvent />
|
||||
<PreBuildEvent>
|
||||
<Command>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</Command>
|
||||
</PreBuildEvent>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|ARM'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<Optimization>MaxSpeed</Optimization>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>NDEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<TreatWarningAsError>true</TreatWarningAsError>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<PrecompiledHeaderFile>
|
||||
</PrecompiledHeaderFile>
|
||||
<PrecompiledHeaderOutputFile>
|
||||
</PrecompiledHeaderOutputFile>
|
||||
<ProgramDataBaseFileName>$(OutputPath)$(TargetName).pdb</ProgramDataBaseFileName>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<PostBuildEvent />
|
||||
<PreBuildEvent>
|
||||
<Command>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</Command>
|
||||
</PreBuildEvent>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='ReleaseMD|ARM64'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<Optimization>MaxSpeed</Optimization>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>NDEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<TreatWarningAsError>true</TreatWarningAsError>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<PrecompiledHeaderFile/>
|
||||
<PrecompiledHeaderOutputFile/>
|
||||
<ProgramDataBaseFileName>$(OutputPath)$(TargetName).pdb</ProgramDataBaseFileName>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<PostBuildEvent />
|
||||
<PreBuildEvent>
|
||||
<Command>SET DETOURS_TARGET_PROCESSOR=$(PlatformTarget)
|
||||
cd ..
|
||||
nmake</Command>
|
||||
</PreBuildEvent>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="..\samples\comeasy\comeasy.cpp" />
|
||||
<ClCompile Include="..\samples\comeasy\wrotei.cpp" />
|
||||
<ClCompile Include="..\samples\commem\commem.cpp" />
|
||||
<ClCompile Include="..\samples\cping\cping.cpp" />
|
||||
<ClCompile Include="..\samples\disas\disas.cpp" />
|
||||
<ClCompile Include="..\samples\disas\unk.cpp" />
|
||||
<ClCompile Include="..\samples\disas\x86.cpp" />
|
||||
<ClCompile Include="..\samples\dtest\dtarge.cpp" />
|
||||
<ClCompile Include="..\samples\dtest\dtest.cpp" />
|
||||
<ClCompile Include="..\samples\dumpe\dumpe.cpp" />
|
||||
<ClCompile Include="..\samples\dumpi\dumpi.cpp" />
|
||||
<ClCompile Include="..\samples\dynamic_alloc\main.cpp" />
|
||||
<ClCompile Include="..\samples\echo\echofx.cpp" />
|
||||
<ClCompile Include="..\samples\echo\echonul.cpp" />
|
||||
<ClCompile Include="..\samples\echo\main.cpp" />
|
||||
<ClCompile Include="..\samples\einst\edll1x.cpp" />
|
||||
<ClCompile Include="..\samples\einst\edll2x.cpp" />
|
||||
<ClCompile Include="..\samples\einst\edll3x.cpp" />
|
||||
<ClCompile Include="..\samples\einst\einst.cpp" />
|
||||
<ClCompile Include="..\samples\excep\excep.cpp" />
|
||||
<ClCompile Include="..\samples\excep\firstexc.cpp" />
|
||||
<ClCompile Include="..\samples\findfunc\extend.cpp" />
|
||||
<ClCompile Include="..\samples\findfunc\findfunc.cpp" />
|
||||
<ClCompile Include="..\samples\findfunc\symtest.cpp" />
|
||||
<ClCompile Include="..\samples\findfunc\target.cpp" />
|
||||
<ClCompile Include="..\samples\impmunge\impmunge.cpp" />
|
||||
<ClCompile Include="..\samples\member\member.cpp" />
|
||||
<ClCompile Include="..\samples\opengl\ogldet.cpp" />
|
||||
<ClCompile Include="..\samples\opengl\testogl.cpp" />
|
||||
<ClCompile Include="..\samples\region\region.cpp" />
|
||||
<ClCompile Include="..\samples\setdll\setdll.cpp" />
|
||||
<ClCompile Include="..\samples\simple\simple.cpp" />
|
||||
<ClCompile Include="..\samples\simple\sleep5.cpp" />
|
||||
<ClCompile Include="..\samples\simple_safe\simple_safe.cpp" />
|
||||
<ClCompile Include="..\samples\simple_safe\sleep5.cpp" />
|
||||
<ClCompile Include="..\samples\slept\dslept.cpp" />
|
||||
<ClCompile Include="..\samples\slept\sleepbed.cpp" />
|
||||
<ClCompile Include="..\samples\slept\sleepnew.cpp" />
|
||||
<ClCompile Include="..\samples\slept\sleepold.cpp" />
|
||||
<ClCompile Include="..\samples\slept\slept.cpp" />
|
||||
<ClCompile Include="..\samples\slept\verify.cpp" />
|
||||
<ClCompile Include="..\samples\syelog\sltest.cpp" />
|
||||
<ClCompile Include="..\samples\syelog\sltestp.cpp" />
|
||||
<ClCompile Include="..\samples\syelog\syelog.cpp" />
|
||||
<ClCompile Include="..\samples\syelog\syelogd.cpp" />
|
||||
<ClCompile Include="..\samples\talloc\talloc.cpp" />
|
||||
<ClCompile Include="..\samples\talloc\tdll1x.cpp" />
|
||||
<ClCompile Include="..\samples\talloc\tdll2x.cpp" />
|
||||
<ClCompile Include="..\samples\talloc\tdll3x.cpp" />
|
||||
<ClCompile Include="..\samples\talloc\tdll4x.cpp" />
|
||||
<ClCompile Include="..\samples\talloc\tdll5x.cpp" />
|
||||
<ClCompile Include="..\samples\talloc\tdll6x.cpp" />
|
||||
<ClCompile Include="..\samples\talloc\tdll7x.cpp" />
|
||||
<ClCompile Include="..\samples\talloc\tdll8x.cpp" />
|
||||
<ClCompile Include="..\samples\talloc\tdll9x.cpp" />
|
||||
<ClCompile Include="..\samples\traceapi\testapi.cpp" />
|
||||
<ClCompile Include="..\samples\traceapi\trcapi.cpp" />
|
||||
<ClCompile Include="..\samples\traceapi\_win32.cpp" />
|
||||
<ClCompile Include="..\samples\tracebld\tracebld.cpp" />
|
||||
<ClCompile Include="..\samples\tracebld\trcbld.cpp" />
|
||||
<ClCompile Include="..\samples\tracelnk\trclnk.cpp" />
|
||||
<ClCompile Include="..\samples\tracemem\trcmem.cpp" />
|
||||
<ClCompile Include="..\samples\tracereg\trcreg.cpp" />
|
||||
<ClCompile Include="..\samples\traceser\trcser.cpp" />
|
||||
<ClCompile Include="..\samples\tracessl\trcssl.cpp" />
|
||||
<ClCompile Include="..\samples\tracetcp\trctcp.cpp" />
|
||||
<ClCompile Include="..\samples\tryman\size.cpp" />
|
||||
<ClCompile Include="..\samples\tryman\tryman.cpp" />
|
||||
<ClCompile Include="..\samples\tryman\tstman.cpp" />
|
||||
<ClCompile Include="..\samples\withdll\withdll.cpp" />
|
||||
<ClCompile Include="..\src\creatwth.cpp" />
|
||||
<ClCompile Include="..\src\detours.cpp" />
|
||||
<ClCompile Include="..\src\disasm.cpp" />
|
||||
<ClCompile Include="..\src\disolarm.cpp" />
|
||||
<ClCompile Include="..\src\disolarm64.cpp" />
|
||||
<ClCompile Include="..\src\disolia64.cpp" />
|
||||
<ClCompile Include="..\src\disolx64.cpp" />
|
||||
<ClCompile Include="..\src\disolx86.cpp" />
|
||||
<ClCompile Include="..\src\image.cpp" />
|
||||
<ClCompile Include="..\src\modules.cpp" />
|
||||
<ClCompile Include="..\src\uimports.cpp">
|
||||
<ExcludedFromBuild>true</ExcludedFromBuild>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="..\samples\dtest\dtarge.h" />
|
||||
<ClInclude Include="..\samples\excep\firstexc.h" />
|
||||
<ClInclude Include="..\samples\findfunc\target.h" />
|
||||
<ClInclude Include="..\samples\slept\slept.h" />
|
||||
<ClInclude Include="..\samples\syelog\syelog.h" />
|
||||
<ClInclude Include="..\samples\tracebld\tracebld.h" />
|
||||
<ClInclude Include="..\src\detours.h" />
|
||||
<ClInclude Include="..\src\detver.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="..\.gitignore" />
|
||||
<None Include="..\LICENSE.md" />
|
||||
<None Include="..\Makefile" />
|
||||
<None Include="..\README.md" />
|
||||
<None Include="..\samples\comeasy\Makefile" />
|
||||
<None Include="..\samples\commem\Makefile" />
|
||||
<None Include="..\samples\common.mak" />
|
||||
<None Include="..\samples\cping\cping.dat" />
|
||||
<None Include="..\samples\cping\Makefile" />
|
||||
<None Include="..\samples\disas\arm.asm" />
|
||||
<None Include="..\samples\disas\ia64.asm" />
|
||||
<None Include="..\samples\disas\Makefile" />
|
||||
<None Include="..\samples\disas\x64.asm" />
|
||||
<None Include="..\samples\dtest\Makefile" />
|
||||
<None Include="..\samples\dumpe\Makefile" />
|
||||
<None Include="..\samples\dumpi\Makefile" />
|
||||
<None Include="..\samples\dynamic_alloc\Makefile" />
|
||||
<None Include="..\samples\dynamic_alloc\x64.asm" />
|
||||
<None Include="..\samples\dynamic_alloc\x86.asm" />
|
||||
<None Include="..\samples\echo\Makefile" />
|
||||
<None Include="..\samples\einst\Makefile" />
|
||||
<None Include="..\samples\excep\Makefile" />
|
||||
<None Include="..\samples\findfunc\Makefile" />
|
||||
<None Include="..\samples\impmunge\Makefile" />
|
||||
<None Include="..\samples\Makefile" />
|
||||
<None Include="..\samples\member\Makefile" />
|
||||
<None Include="..\samples\opengl\Makefile" />
|
||||
<None Include="..\samples\region\Makefile" />
|
||||
<None Include="..\samples\setdll\Makefile" />
|
||||
<None Include="..\samples\simple\Makefile" />
|
||||
<None Include="..\samples\simple_safe\Makefile" />
|
||||
<None Include="..\samples\slept\Makefile" />
|
||||
<None Include="..\samples\syelog\Makefile" />
|
||||
<None Include="..\samples\talloc\Makefile" />
|
||||
<None Include="..\samples\traceapi\Makefile" />
|
||||
<None Include="..\samples\tracebld\Makefile" />
|
||||
<None Include="..\samples\tracelnk\Makefile" />
|
||||
<None Include="..\samples\tracemem\Makefile" />
|
||||
<None Include="..\samples\tracereg\Makefile" />
|
||||
<None Include="..\samples\traceser\Makefile" />
|
||||
<None Include="..\samples\tracessl\Makefile" />
|
||||
<None Include="..\samples\tracetcp\Makefile" />
|
||||
<None Include="..\samples\tryman\Makefile" />
|
||||
<None Include="..\samples\tryman\managed.cs" />
|
||||
<None Include="..\samples\withdll\Makefile" />
|
||||
<None Include="..\system.mak" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="..\CREDITS.md" />
|
||||
<Text Include="..\samples\cping\ReadMe.Txt" />
|
||||
<Text Include="..\samples\dtest\NORMAL_IA64.TXT" />
|
||||
<Text Include="..\samples\dtest\NORMAL_X64.TXT" />
|
||||
<Text Include="..\samples\dtest\NORMAL_X86.TXT" />
|
||||
<Text Include="..\samples\README.TXT" />
|
||||
<Text Include="..\samples\slept\NORMAL_IA64.TXT" />
|
||||
<Text Include="..\samples\slept\NORMAL_X64.TXT" />
|
||||
<Text Include="..\samples\slept\NORMAL_X86.TXT" />
|
||||
<Text Include="..\samples\talloc\NORMAL_IA64.TXT" />
|
||||
<Text Include="..\samples\talloc\NORMAL_X64.TXT" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="..\samples\comeasy\wrotei.rc" />
|
||||
<ResourceCompile Include="..\samples\dtest\dtarge.rc" />
|
||||
<ResourceCompile Include="..\samples\echo\echofx.rc" />
|
||||
<ResourceCompile Include="..\samples\findfunc\extend.rc" />
|
||||
<ResourceCompile Include="..\samples\findfunc\target.rc" />
|
||||
<ResourceCompile Include="..\samples\opengl\ogldet.rc" />
|
||||
<ResourceCompile Include="..\samples\simple\simple.rc" />
|
||||
<ResourceCompile Include="..\samples\simple_safe\simple_safe.rc" />
|
||||
<ResourceCompile Include="..\samples\slept\dslept.rc" />
|
||||
<ResourceCompile Include="..\samples\slept\slept.rc" />
|
||||
<ResourceCompile Include="..\samples\traceapi\trcapi.rc" />
|
||||
<ResourceCompile Include="..\samples\tracebld\trcbld.rc" />
|
||||
<ResourceCompile Include="..\samples\tracelnk\trclnk.rc" />
|
||||
<ResourceCompile Include="..\samples\tracemem\trcmem.rc" />
|
||||
<ResourceCompile Include="..\samples\tracereg\trcreg.rc" />
|
||||
<ResourceCompile Include="..\samples\traceser\trcser.rc" />
|
||||
<ResourceCompile Include="..\samples\tracessl\trcssl.rc" />
|
||||
<ResourceCompile Include="..\samples\tracetcp\trctcp.rc" />
|
||||
<ResourceCompile Include="..\samples\tryman\tstman.rc" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Midl Include="..\samples\cping\iping.idl" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
</Project>
|
||||
+605
@@ -0,0 +1,605 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup>
|
||||
<Filter Include="samples">
|
||||
<UniqueIdentifier>{4DE3849F-647A-48FF-8873-256D44DFF3CA}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\comeasy">
|
||||
<UniqueIdentifier>{6215A674-4251-4F64-AA56-6F80297E5F8B}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\commem">
|
||||
<UniqueIdentifier>{B581B77F-AE4D-43BC-8C4F-EDE0E61EFFD3}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\cping">
|
||||
<UniqueIdentifier>{BF2ACC0E-890D-4BD0-B532-6228AF011E3E}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\disas">
|
||||
<UniqueIdentifier>{32F50667-320C-4799-B7DA-D1878C358D64}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\dtest">
|
||||
<UniqueIdentifier>{314C251E-4D8E-4837-9C36-4741399ED2A1}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\dumpe">
|
||||
<UniqueIdentifier>{53C9A890-D5AB-4FD1-B898-6107C0E676E7}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\dumpi">
|
||||
<UniqueIdentifier>{17467834-9161-4FB2-BBEF-E3233CBBC818}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\dynamic_alloc">
|
||||
<UniqueIdentifier>{5A3371DC-E827-47CC-901A-F3D91162EFB2}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\echo">
|
||||
<UniqueIdentifier>{A2B9B912-8C03-400F-B271-51EEB4CE6843}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\einst">
|
||||
<UniqueIdentifier>{571B99A3-B6D5-4838-B189-4A038B104B2A}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\excep">
|
||||
<UniqueIdentifier>{F1740406-C1BB-49C7-A602-9DDACBD4ABCA}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\findfunc">
|
||||
<UniqueIdentifier>{58CCECE5-A38B-4C56-8E3F-3E0722393F56}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\impmunge">
|
||||
<UniqueIdentifier>{B3E06AC8-3F78-43C8-B7AC-84546475F960}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\member">
|
||||
<UniqueIdentifier>{CD32F55E-60C5-4ED6-ACCC-4B43E6AC195D}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\opengl">
|
||||
<UniqueIdentifier>{1ABFBA92-4E60-481A-9007-8150D95E072F}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\region">
|
||||
<UniqueIdentifier>{0929821A-9C85-4D74-B969-865D6DA40D2A}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\setdll">
|
||||
<UniqueIdentifier>{9017F1FA-4DCB-44D1-854D-2F14358791F5}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\simple">
|
||||
<UniqueIdentifier>{D9D7E0B0-4E14-473F-AE28-B4A5AF4EB427}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\simple_safe">
|
||||
<UniqueIdentifier>{1F157B88-D9DA-41E3-9B18-FC5600777FB1}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\slept">
|
||||
<UniqueIdentifier>{88EFC740-5E28-484E-97FC-E7BBA6D36454}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\syelog">
|
||||
<UniqueIdentifier>{EA900A65-64CA-417B-8DE7-4174C9CB1E5A}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\talloc">
|
||||
<UniqueIdentifier>{7A1582F0-0A25-4A0E-B7E5-14F6E332BDFA}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\traceapi">
|
||||
<UniqueIdentifier>{B99E03FF-320A-4D13-BFB8-674E102E306D}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\tracebld">
|
||||
<UniqueIdentifier>{6169E241-5297-4B63-8D32-407D592EF103}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\tracelnk">
|
||||
<UniqueIdentifier>{EFD841EC-A8B1-4CD6-AC2D-0D286669BA3B}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\tracemem">
|
||||
<UniqueIdentifier>{14F0CAFF-0470-4D28-9083-3FD5656E7B27}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\tracereg">
|
||||
<UniqueIdentifier>{A3CE1454-F707-4A29-B389-2E762651CDD7}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\traceser">
|
||||
<UniqueIdentifier>{D3299D5A-9CE3-45E6-9784-4166606BA70B}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\tracessl">
|
||||
<UniqueIdentifier>{6E1471A7-7B40-4528-8210-64CFC4663258}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\tracetcp">
|
||||
<UniqueIdentifier>{62236214-1B41-4765-9D9D-1E313B4E5AB7}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\tryman">
|
||||
<UniqueIdentifier>{24AC6634-A8C9-430B-8D95-45DEB57070C9}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="samples\withdll">
|
||||
<UniqueIdentifier>{077E7134-5AA3-4151-8313-88106FCBDAB3}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="src">
|
||||
<UniqueIdentifier>{E980771B-0BA5-4B01-947A-B99D33E31E89}</UniqueIdentifier>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="..\src\uimports.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\creatwth.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\detours.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\disasm.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\disolarm.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\disolarm64.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\disolia64.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\disolx64.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\disolx86.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\image.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\src\modules.cpp">
|
||||
<Filter>src</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\tryman\size.cpp">
|
||||
<Filter>samples\tryman</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\tracebld\tracebld.cpp">
|
||||
<Filter>samples\tracebld</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\tracebld\trcbld.cpp">
|
||||
<Filter>samples\tracebld</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\tracelnk\trclnk.cpp">
|
||||
<Filter>samples\tracelnk</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\tracemem\trcmem.cpp">
|
||||
<Filter>samples\tracemem</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\tracereg\trcreg.cpp">
|
||||
<Filter>samples\tracereg</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\traceser\trcser.cpp">
|
||||
<Filter>samples\traceser</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\tracessl\trcssl.cpp">
|
||||
<Filter>samples\tracessl</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\tracetcp\trctcp.cpp">
|
||||
<Filter>samples\tracetcp</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\tryman\tryman.cpp">
|
||||
<Filter>samples\tryman</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\tryman\tstman.cpp">
|
||||
<Filter>samples\tryman</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\withdll\withdll.cpp">
|
||||
<Filter>samples\withdll</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\traceapi\_win32.cpp">
|
||||
<Filter>samples\traceapi</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\slept\dslept.cpp">
|
||||
<Filter>samples\slept</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\simple\simple.cpp">
|
||||
<Filter>samples\simple</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\simple\sleep5.cpp">
|
||||
<Filter>samples\simple</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\simple_safe\simple_safe.cpp">
|
||||
<Filter>samples\simple_safe</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\simple_safe\sleep5.cpp">
|
||||
<Filter>samples\simple_safe</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\slept\sleepbed.cpp">
|
||||
<Filter>samples\slept</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\slept\sleepnew.cpp">
|
||||
<Filter>samples\slept</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\slept\sleepold.cpp">
|
||||
<Filter>samples\slept</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\slept\slept.cpp">
|
||||
<Filter>samples\slept</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\syelog\sltest.cpp">
|
||||
<Filter>samples\syelog</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\syelog\sltestp.cpp">
|
||||
<Filter>samples\syelog</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\syelog\syelog.cpp">
|
||||
<Filter>samples\syelog</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\syelog\syelogd.cpp">
|
||||
<Filter>samples\syelog</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\talloc\talloc.cpp">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\talloc\tdll1x.cpp">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\talloc\tdll2x.cpp">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\talloc\tdll3x.cpp">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\talloc\tdll4x.cpp">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\talloc\tdll5x.cpp">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\talloc\tdll6x.cpp">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\talloc\tdll7x.cpp">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\talloc\tdll8x.cpp">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\talloc\tdll9x.cpp">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\traceapi\testapi.cpp">
|
||||
<Filter>samples\traceapi</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\traceapi\trcapi.cpp">
|
||||
<Filter>samples\traceapi</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\slept\verify.cpp">
|
||||
<Filter>samples\slept</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\dtest\dtarge.cpp">
|
||||
<Filter>samples\dtest</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\dtest\dtest.cpp">
|
||||
<Filter>samples\dtest</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\dumpe\dumpe.cpp">
|
||||
<Filter>samples\dumpe</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\dumpi\dumpi.cpp">
|
||||
<Filter>samples\dumpi</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\echo\echofx.cpp">
|
||||
<Filter>samples\echo</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\echo\echonul.cpp">
|
||||
<Filter>samples\echo</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\einst\edll1x.cpp">
|
||||
<Filter>samples\einst</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\einst\edll2x.cpp">
|
||||
<Filter>samples\einst</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\einst\edll3x.cpp">
|
||||
<Filter>samples\einst</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\einst\einst.cpp">
|
||||
<Filter>samples\einst</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\excep\excep.cpp">
|
||||
<Filter>samples\excep</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\findfunc\extend.cpp">
|
||||
<Filter>samples\findfunc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\findfunc\findfunc.cpp">
|
||||
<Filter>samples\findfunc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\excep\firstexc.cpp">
|
||||
<Filter>samples\excep</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\impmunge\impmunge.cpp">
|
||||
<Filter>samples\impmunge</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\dynamic_alloc\main.cpp">
|
||||
<Filter>samples\dynamic_alloc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\echo\main.cpp">
|
||||
<Filter>samples\echo</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\member\member.cpp">
|
||||
<Filter>samples\member</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\opengl\ogldet.cpp">
|
||||
<Filter>samples\opengl</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\region\region.cpp">
|
||||
<Filter>samples\region</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\setdll\setdll.cpp">
|
||||
<Filter>samples\setdll</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\findfunc\symtest.cpp">
|
||||
<Filter>samples\findfunc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\findfunc\target.cpp">
|
||||
<Filter>samples\findfunc</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\opengl\testogl.cpp">
|
||||
<Filter>samples\opengl</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\comeasy\comeasy.cpp">
|
||||
<Filter>samples\comeasy</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\commem\commem.cpp">
|
||||
<Filter>samples\commem</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\cping\cping.cpp">
|
||||
<Filter>samples\cping</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\disas\disas.cpp">
|
||||
<Filter>samples\disas</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\disas\unk.cpp">
|
||||
<Filter>samples\disas</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\comeasy\wrotei.cpp">
|
||||
<Filter>samples\comeasy</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="..\samples\disas\x86.cpp">
|
||||
<Filter>samples\disas</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="..\src\detours.h">
|
||||
<Filter>src</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="..\src\detver.h">
|
||||
<Filter>src</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="..\samples\tracebld\tracebld.h">
|
||||
<Filter>samples\tracebld</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="..\samples\slept\slept.h">
|
||||
<Filter>samples\slept</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="..\samples\syelog\syelog.h">
|
||||
<Filter>samples\syelog</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="..\samples\dtest\dtarge.h">
|
||||
<Filter>samples\dtest</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="..\samples\excep\firstexc.h">
|
||||
<Filter>samples\excep</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="..\samples\findfunc\target.h">
|
||||
<Filter>samples\findfunc</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="..\samples\tracebld\Makefile">
|
||||
<Filter>samples\tracebld</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\tracelnk\Makefile">
|
||||
<Filter>samples\tracelnk</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\tracemem\Makefile">
|
||||
<Filter>samples\tracemem</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\tracereg\Makefile">
|
||||
<Filter>samples\tracereg</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\traceser\Makefile">
|
||||
<Filter>samples\traceser</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\tracessl\Makefile">
|
||||
<Filter>samples\tracessl</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\tracetcp\Makefile">
|
||||
<Filter>samples\tracetcp</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\tryman\Makefile">
|
||||
<Filter>samples\tryman</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\withdll\Makefile">
|
||||
<Filter>samples\withdll</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\tryman\managed.cs">
|
||||
<Filter>samples\tryman</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\simple\Makefile">
|
||||
<Filter>samples\simple</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\simple_safe\Makefile">
|
||||
<Filter>samples\simple_safe</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\slept\Makefile">
|
||||
<Filter>samples\slept</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\syelog\Makefile">
|
||||
<Filter>samples\syelog</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\talloc\Makefile">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\traceapi\Makefile">
|
||||
<Filter>samples\traceapi</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\dumpe\Makefile">
|
||||
<Filter>samples\dumpe</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\dumpi\Makefile">
|
||||
<Filter>samples\dumpi</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\dynamic_alloc\Makefile">
|
||||
<Filter>samples\dynamic_alloc</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\echo\Makefile">
|
||||
<Filter>samples\echo</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\einst\Makefile">
|
||||
<Filter>samples\einst</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\excep\Makefile">
|
||||
<Filter>samples\excep</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\findfunc\Makefile">
|
||||
<Filter>samples\findfunc</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\impmunge\Makefile">
|
||||
<Filter>samples\impmunge</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\member\Makefile">
|
||||
<Filter>samples\member</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\opengl\Makefile">
|
||||
<Filter>samples\opengl</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\region\Makefile">
|
||||
<Filter>samples\region</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\setdll\Makefile">
|
||||
<Filter>samples\setdll</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\dynamic_alloc\x64.asm">
|
||||
<Filter>samples\dynamic_alloc</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\dynamic_alloc\x86.asm">
|
||||
<Filter>samples\dynamic_alloc</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\disas\arm.asm">
|
||||
<Filter>samples\disas</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\common.mak">
|
||||
<Filter>samples</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\cping\cping.dat">
|
||||
<Filter>samples\cping</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\disas\ia64.asm">
|
||||
<Filter>samples\disas</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\comeasy\Makefile">
|
||||
<Filter>samples\comeasy</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\commem\Makefile">
|
||||
<Filter>samples\commem</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\cping\Makefile">
|
||||
<Filter>samples\cping</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\disas\Makefile">
|
||||
<Filter>samples\disas</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\dtest\Makefile">
|
||||
<Filter>samples\dtest</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\Makefile">
|
||||
<Filter>samples</Filter>
|
||||
</None>
|
||||
<None Include="..\samples\disas\x64.asm">
|
||||
<Filter>samples\disas</Filter>
|
||||
</None>
|
||||
<None Include="..\.gitignore" />
|
||||
<None Include="..\LICENSE.md" />
|
||||
<None Include="..\Makefile" />
|
||||
<None Include="..\README.md" />
|
||||
<None Include="..\system.mak" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Text Include="..\samples\slept\NORMAL_IA64.TXT">
|
||||
<Filter>samples\slept</Filter>
|
||||
</Text>
|
||||
<Text Include="..\samples\talloc\NORMAL_IA64.TXT">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</Text>
|
||||
<Text Include="..\samples\slept\NORMAL_X64.TXT">
|
||||
<Filter>samples\slept</Filter>
|
||||
</Text>
|
||||
<Text Include="..\samples\talloc\NORMAL_X64.TXT">
|
||||
<Filter>samples\talloc</Filter>
|
||||
</Text>
|
||||
<Text Include="..\samples\slept\NORMAL_X86.TXT">
|
||||
<Filter>samples\slept</Filter>
|
||||
</Text>
|
||||
<Text Include="..\samples\dtest\NORMAL_IA64.TXT">
|
||||
<Filter>samples\dtest</Filter>
|
||||
</Text>
|
||||
<Text Include="..\samples\dtest\NORMAL_X64.TXT">
|
||||
<Filter>samples\dtest</Filter>
|
||||
</Text>
|
||||
<Text Include="..\samples\dtest\NORMAL_X86.TXT">
|
||||
<Filter>samples\dtest</Filter>
|
||||
</Text>
|
||||
<Text Include="..\samples\cping\ReadMe.Txt">
|
||||
<Filter>samples\cping</Filter>
|
||||
</Text>
|
||||
<Text Include="..\samples\README.TXT">
|
||||
<Filter>samples</Filter>
|
||||
</Text>
|
||||
<Text Include="..\CREDITS.md" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="..\samples\traceapi\trcapi.rc">
|
||||
<Filter>samples\traceapi</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\tracebld\trcbld.rc">
|
||||
<Filter>samples\tracebld</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\tracelnk\trclnk.rc">
|
||||
<Filter>samples\tracelnk</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\tracemem\trcmem.rc">
|
||||
<Filter>samples\tracemem</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\tracereg\trcreg.rc">
|
||||
<Filter>samples\tracereg</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\traceser\trcser.rc">
|
||||
<Filter>samples\traceser</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\tracessl\trcssl.rc">
|
||||
<Filter>samples\tracessl</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\tracetcp\trctcp.rc">
|
||||
<Filter>samples\tracetcp</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\tryman\tstman.rc">
|
||||
<Filter>samples\tryman</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\slept\dslept.rc">
|
||||
<Filter>samples\slept</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\simple\simple.rc">
|
||||
<Filter>samples\simple</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\simple_safe\simple_safe.rc">
|
||||
<Filter>samples\simple_safe</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\slept\slept.rc">
|
||||
<Filter>samples\slept</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\dtest\dtarge.rc">
|
||||
<Filter>samples\dtest</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\echo\echofx.rc">
|
||||
<Filter>samples\echo</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\findfunc\extend.rc">
|
||||
<Filter>samples\findfunc</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\opengl\ogldet.rc">
|
||||
<Filter>samples\opengl</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\findfunc\target.rc">
|
||||
<Filter>samples\findfunc</Filter>
|
||||
</ResourceCompile>
|
||||
<ResourceCompile Include="..\samples\comeasy\wrotei.rc">
|
||||
<Filter>samples\comeasy</Filter>
|
||||
</ResourceCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<Midl Include="..\samples\cping\iping.idl">
|
||||
<Filter>samples\cping</Filter>
|
||||
</Midl>
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
Vendored
+43
@@ -0,0 +1,43 @@
|
||||
|
||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio Version 17
|
||||
VisualStudioVersion = 17.0.31903.59
|
||||
MinimumVisualStudioVersion = 10.0.40219.1
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "plutosvg", "plutosvg\plutosvg.vcxproj", "{0FB29240-171B-41E9-B255-95BE753D0EB2}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|ARM = Debug|ARM
|
||||
Debug|ARM64 = Debug|ARM64
|
||||
Debug|x64 = Debug|x64
|
||||
Debug|x86 = Debug|x86
|
||||
Release|ARM = Release|ARM
|
||||
Release|ARM64 = Release|ARM64
|
||||
Release|x64 = Release|x64
|
||||
Release|x86 = Release|x86
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Debug|ARM.ActiveCfg = Debug|ARM
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Debug|ARM.Build.0 = Debug|ARM
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Debug|ARM64.ActiveCfg = Debug|ARM64
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Debug|ARM64.Build.0 = Debug|ARM64
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Debug|x64.ActiveCfg = Debug|x64
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Debug|x64.Build.0 = Debug|x64
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Debug|x86.ActiveCfg = Debug|Win32
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Debug|x86.Build.0 = Debug|Win32
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Release|ARM.ActiveCfg = Release|ARM
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Release|ARM.Build.0 = Release|ARM
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Release|ARM64.ActiveCfg = Release|ARM64
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Release|ARM64.Build.0 = Release|ARM64
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Release|x64.ActiveCfg = Release|x64
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Release|x64.Build.0 = Release|x64
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Release|x86.ActiveCfg = Release|Win32
|
||||
{0FB29240-171B-41E9-B255-95BE753D0EB2}.Release|x86.Build.0 = Release|Win32
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
SolutionGuid = {2B021D4C-7D18-41AB-BA19-8F6DC4160B22}
|
||||
EndGlobalSection
|
||||
EndGlobal
|
||||
+63
@@ -0,0 +1,63 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
|
||||
<!--
|
||||
作者:mingkuang
|
||||
修改日期:2018-08-14
|
||||
|
||||
|
||||
VC-LTL自动化加载配置,建议你将此文件单独复制到你的工程再使用,该文件能自动识别当前环境是否存在VC-LTL,并且自动应用。
|
||||
|
||||
使用方法:
|
||||
1. 在属性管理器选择所有Release配置,然后右键选择“添加现有属性表”。
|
||||
2. 务必保证所有依赖的静态库也均用VC-LTL重新编译。
|
||||
|
||||
|
||||
VC-LTL默认搜索顺序
|
||||
1. VC-LTL.props所在目录,即 $(MSBuildThisFileDirectory)
|
||||
2. 当前项目根目录,即 $(ProjectDir)VC-LTL
|
||||
3. 前解决方案根目录,即 $(SolutionDir)VC-LTL
|
||||
4. 当前项目父目录,即 $(ProjectDir)..\VC-LTL
|
||||
5. 当前解决方案父目录,即 $(SolutionDir)..\VC-LTL
|
||||
6. 注册表HKEY_CURRENT_USER\Code\VC-LTL@Root
|
||||
|
||||
把VC-LTL放在其中一个位置即可,VC-LTL就能被自动引用。
|
||||
|
||||
如果你对默认搜索顺序不满,你可以修改此文件。你也可以直接指定$(VC_LTL_Root)宏更加任性的去加载VC-LTL。
|
||||
|
||||
-->
|
||||
|
||||
<!--#####################################################################VC-LTL设置#####################################################################-->
|
||||
<PropertyGroup>
|
||||
<!--<DisableAdvancedSupport>true</DisableAdvancedSupport>-->
|
||||
<SupportWinXP>false</SupportWinXP>
|
||||
</PropertyGroup>
|
||||
|
||||
|
||||
<PropertyGroup>
|
||||
<!--Shared.props文件根目录存在VC-LTL?-->
|
||||
<VC_LTL_Root Condition=" ('$(VC_LTL_Root)'=='') And (Exists('$(MSBuildThisFileDirectory)_msvcrt.h')) ">$(MSBuildThisFileDirectory)</VC_LTL_Root>
|
||||
|
||||
<!--当前项目根目录存在VC-LTL?-->
|
||||
<VC_LTL_Root Condition=" ('$(VC_LTL_Root)'=='') And (Exists('$(ProjectDir)VC-LTL\_msvcrt.h')) ">$(ProjectDir)VC-LTL</VC_LTL_Root>
|
||||
|
||||
<!--当前解决方案根目录存在VC-LTL?-->
|
||||
<VC_LTL_Root Condition=" ('$(VC_LTL_Root)'=='') And ('$(SolutionDir)'!='') And (Exists('$(SolutionDir)VC-LTL\_msvcrt.h')) ">$(SolutionDir)VC-LTL</VC_LTL_Root>
|
||||
|
||||
<!--当前项目父目录存在VC-LTL?-->
|
||||
<VC_LTL_Root Condition=" ('$(VC_LTL_Root)'=='') And (Exists('$(ProjectDir)..\VC-LTL\_msvcrt.h')) ">$(ProjectDir)..\VC-LTL</VC_LTL_Root>
|
||||
|
||||
<!--当前解决方案父目录存在VC-LTL?-->
|
||||
<VC_LTL_Root Condition=" ('$(VC_LTL_Root)'=='') And ('$(SolutionDir)'!='') And (Exists('$(SolutionDir)..\VC-LTL\_msvcrt.h')) ">$(SolutionDir)..\VC-LTL</VC_LTL_Root>
|
||||
|
||||
<!--如果本地工程没有,那么继续尝试通过注册表获取VC-LTL路径,双击Install.cmd可以自动产生此注册表。-->
|
||||
<VC_LTL_Root Condition=" '$(VC_LTL_Root)'=='' ">$(Registry:HKEY_CURRENT_USER\Code\VC-LTL@Root)</VC_LTL_Root>
|
||||
</PropertyGroup>
|
||||
|
||||
<ImportGroup Condition=" '$(VC_LTL_Root)'!=''">
|
||||
<Import Project="$(VC_LTL_Root)\Config\config.props" Condition="Exists('$(VC_LTL_Root)\Config\config.props')"/>
|
||||
|
||||
<!--兼容模式,尝试加载老版本-->
|
||||
<Import Project="$(VC_LTL_Root)\ltlvcrt.props" Condition="(!Exists('$(VC_LTL_Root)\Config\config.props')) And (Exists('$(VC_LTL_Root)\ltlvcrt.props'))"/>
|
||||
</ImportGroup>
|
||||
</Project>
|
||||
+198
@@ -0,0 +1,198 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="Release|ARM">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>ARM</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|ARM64">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>ARM64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|Win32">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="Release|x64">
|
||||
<Configuration>Release</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<VCProjectVersion>16.0</VCProjectVersion>
|
||||
<Keyword>Win32Proj</Keyword>
|
||||
<ProjectGuid>{0fb29240-171b-41e9-b255-95be753d0eb2}</ProjectGuid>
|
||||
<RootNamespace>plutosvg</RootNamespace>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup>
|
||||
<ConfigurationType>StaticLibrary</ConfigurationType>
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<PlatformToolset>v143</PlatformToolset>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="Shared">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
<Import Project="VC-LTL.props" Condition="'$(Configuration)|$(Platform)'=='Release|$(Platform)'" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup>
|
||||
<LinkIncremental>false</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>WIN32;NDEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>
|
||||
<LanguageStandard>stdcpp20</LanguageStandard>
|
||||
<LanguageStandard_C>stdc17</LanguageStandard_C>
|
||||
<CallingConvention>StdCall</CallingConvention>
|
||||
<DebugInformationFormat>None</DebugInformationFormat>
|
||||
<WholeProgramOptimization>false</WholeProgramOptimization>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<MinimalRebuild>false</MinimalRebuild>
|
||||
<CompileAs>CompileAsC</CompileAs>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>
|
||||
</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<Lib>
|
||||
<OutputFile>$(OutDir)$(TargetName)$(TargetExt)</OutputFile>
|
||||
</Lib>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|ARM'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level3</WarningLevel>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>NDEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>
|
||||
<LanguageStandard>stdcpp20</LanguageStandard>
|
||||
<LanguageStandard_C>stdc17</LanguageStandard_C>
|
||||
<CallingConvention>StdCall</CallingConvention>
|
||||
<DebugInformationFormat>None</DebugInformationFormat>
|
||||
<WholeProgramOptimization>false</WholeProgramOptimization>
|
||||
<SuppressStartupBanner>false</SuppressStartupBanner>
|
||||
<CompileAs>CompileAsC</CompileAs>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>
|
||||
</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<Lib>
|
||||
<SuppressStartupBanner>false</SuppressStartupBanner>
|
||||
<OutputFile>$(OutDir)$(TargetName)-$(Platform)$(TargetExt)</OutputFile>
|
||||
</Lib>
|
||||
<Xdcmake>
|
||||
<SuppressStartupBanner>false</SuppressStartupBanner>
|
||||
</Xdcmake>
|
||||
<Bscmake>
|
||||
<SuppressStartupBanner>false</SuppressStartupBanner>
|
||||
</Bscmake>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>NDEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<CompileAs>CompileAsC</CompileAs>
|
||||
<FavorSizeOrSpeed>Size</FavorSizeOrSpeed>
|
||||
<WholeProgramOptimization>false</WholeProgramOptimization>
|
||||
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>
|
||||
<CallingConvention>StdCall</CallingConvention>
|
||||
<DebugInformationFormat>None</DebugInformationFormat>
|
||||
<LanguageStandard>stdcpp20</LanguageStandard>
|
||||
<LanguageStandard_C>stdc17</LanguageStandard_C>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>
|
||||
</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<Lib>
|
||||
<OutputFile>$(OutDir)$(TargetName)$(TargetExt)</OutputFile>
|
||||
</Lib>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|ARM64'">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>NDEBUG;_LIB;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<CompileAs>CompileAsC</CompileAs>
|
||||
<FavorSizeOrSpeed>Size</FavorSizeOrSpeed>
|
||||
<WholeProgramOptimization>false</WholeProgramOptimization>
|
||||
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>
|
||||
<CallingConvention>StdCall</CallingConvention>
|
||||
<DebugInformationFormat>None</DebugInformationFormat>
|
||||
<LanguageStandard>stdcpp20</LanguageStandard>
|
||||
<LanguageStandard_C>stdc17</LanguageStandard_C>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>
|
||||
</SubSystem>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>true</OptimizeReferences>
|
||||
<GenerateDebugInformation>true</GenerateDebugInformation>
|
||||
</Link>
|
||||
<Lib>
|
||||
<OutputFile>$(OutDir)$(TargetName)$(TargetExt)</OutputFile>
|
||||
</Lib>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="source\plutosvg.c" />
|
||||
<ClCompile Include="source\plutovg-blend.c" />
|
||||
<ClCompile Include="source\plutovg-dash.c" />
|
||||
<ClCompile Include="source\plutovg-font.c" />
|
||||
<ClCompile Include="source\plutovg-geometry.c" />
|
||||
<ClCompile Include="source\plutovg-paint.c" />
|
||||
<ClCompile Include="source\plutovg-rle.c" />
|
||||
<ClCompile Include="source\plutovg.c" />
|
||||
<ClCompile Include="source\sw_ft_math.c" />
|
||||
<ClCompile Include="source\sw_ft_raster.c" />
|
||||
<ClCompile Include="source\sw_ft_stroker.c" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="source\plutosvg.h" />
|
||||
<ClInclude Include="source\plutovg-private.h" />
|
||||
<ClInclude Include="source\plutovg.h" />
|
||||
<ClInclude Include="source\stb_truetype.h" />
|
||||
<ClInclude Include="source\sw_ft_math.h" />
|
||||
<ClInclude Include="source\sw_ft_raster.h" />
|
||||
<ClInclude Include="source\sw_ft_stroker.h" />
|
||||
<ClInclude Include="source\sw_ft_types.h" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
<ImportGroup Label="ExtensionTargets">
|
||||
</ImportGroup>
|
||||
<ItemGroup>
|
||||
<None Include="VC-LTL.props" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
@@ -0,0 +1,81 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup>
|
||||
<Filter Include="Source Files">
|
||||
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
|
||||
<Extensions>cpp;c;cc;cxx;c++;cppm;ixx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Header Files">
|
||||
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
|
||||
<Extensions>h;hh;hpp;hxx;h++;hm;inl;inc;ipp;xsd</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Resource Files">
|
||||
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
|
||||
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="source\plutosvg.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="source\plutovg.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="source\plutovg-blend.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="source\plutovg-dash.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="source\plutovg-font.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="source\plutovg-geometry.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="source\plutovg-paint.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="source\plutovg-rle.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="source\sw_ft_math.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="source\sw_ft_raster.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="source\sw_ft_stroker.c">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="source\plutosvg.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="source\plutovg.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="source\plutovg-private.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="source\stb_truetype.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="source\sw_ft_math.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="source\sw_ft_raster.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="source\sw_ft_stroker.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="source\sw_ft_types.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="VC-LTL.props" />
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
@@ -0,0 +1,6 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="Current" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<PropertyGroup>
|
||||
<ShowAllFiles>false</ShowAllFiles>
|
||||
</PropertyGroup>
|
||||
</Project>
|
||||
+3257
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,60 @@
|
||||
#ifndef PLUTOSVG_H
|
||||
#define PLUTOSVG_H
|
||||
|
||||
#include "plutovg.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @brief Load the image from a file in memory
|
||||
* @param data - pointer to the file data in memory
|
||||
* @param size - size of the data to load, in bytes
|
||||
* @param font - font to use for text rendering
|
||||
* @param width - requested width, in pixels
|
||||
* @param height - requested height, in pixels
|
||||
* @param dpi - dots per inch to use for units conversion to pixels
|
||||
* @return pointer to surface object on success, otherwise NULL
|
||||
*/
|
||||
plutovg_surface_t* plutosvg_load_from_memory(const char* data, int size, plutovg_font_t* font, int width, int height, double dpi);
|
||||
|
||||
/**
|
||||
* @brief Load the image from a file on disk
|
||||
* @param filename - path of the image file to load
|
||||
* @param font - font to use for text rendering
|
||||
* @param width - requested width, in pixels
|
||||
* @param height - requested height, in pixels
|
||||
* @param dpi - dots per inch to use for units conversion to pixels
|
||||
* @return pointer to surface object on success, otherwise NULL
|
||||
*/
|
||||
plutovg_surface_t* plutosvg_load_from_file(const char* filename, plutovg_font_t* font, int width, int height, double dpi);
|
||||
|
||||
/**
|
||||
* @brief Get image dimensions from a file in memory
|
||||
* @param data - pointer to the file data in memory
|
||||
* @param size - size of the data to load, in bytes
|
||||
* @param font - font to use for text rendering
|
||||
* @param width - width of the image, in pixels
|
||||
* @param height - height of the image, in pixels
|
||||
* @param dpi - dots per inch to use for units conversion to pixels
|
||||
* @return true on success, otherwise false
|
||||
*/
|
||||
int plutosvg_dimensions_from_memory(const char* data, int size, plutovg_font_t* font, int* width, int* height, double dpi);
|
||||
|
||||
/**
|
||||
* @brief Get image dimensions from a file on disk
|
||||
* @param filename - path of the image file to load
|
||||
* @param font - font to use for text rendering
|
||||
* @param width - width of the image, in pixels
|
||||
* @param height - height of the image, in pixels
|
||||
* @param dpi - dots per inch to use for units conversion to pixels
|
||||
* @return true on success, otherwise false
|
||||
*/
|
||||
int plutosvg_dimensions_from_file(const char* filename, plutovg_font_t* font, int* width, int* height, double dpi);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif // PLUTOSVG_H
|
||||
@@ -0,0 +1,838 @@
|
||||
#include "plutovg-private.h"
|
||||
|
||||
#include <limits.h>
|
||||
#include <math.h>
|
||||
|
||||
#define COLOR_TABLE_SIZE 1024
|
||||
typedef struct {
|
||||
plutovg_spread_method_t spread;
|
||||
plutovg_matrix_t matrix;
|
||||
uint32_t colortable[COLOR_TABLE_SIZE];
|
||||
union {
|
||||
struct {
|
||||
double x1, y1;
|
||||
double x2, y2;
|
||||
} linear;
|
||||
struct {
|
||||
double cx, cy, cr;
|
||||
double fx, fy, fr;
|
||||
} radial;
|
||||
};
|
||||
} gradient_data_t;
|
||||
|
||||
typedef struct {
|
||||
plutovg_matrix_t matrix;
|
||||
uint8_t* data;
|
||||
int width;
|
||||
int height;
|
||||
int stride;
|
||||
int const_alpha;
|
||||
} texture_data_t;
|
||||
|
||||
typedef struct {
|
||||
double dx;
|
||||
double dy;
|
||||
double l;
|
||||
double off;
|
||||
} linear_gradient_values_t;
|
||||
|
||||
typedef struct {
|
||||
double dx;
|
||||
double dy;
|
||||
double dr;
|
||||
double sqrfr;
|
||||
double a;
|
||||
double inv2a;
|
||||
int extended;
|
||||
} radial_gradient_values_t;
|
||||
|
||||
static inline uint32_t premultiply_color(const plutovg_color_t* color, double opacity)
|
||||
{
|
||||
uint32_t alpha = (uint8_t)(color->a * opacity * 255);
|
||||
uint32_t pr = (uint8_t)(color->r * alpha);
|
||||
uint32_t pg = (uint8_t)(color->g * alpha);
|
||||
uint32_t pb = (uint8_t)(color->b * alpha);
|
||||
|
||||
return (alpha << 24) | (pr << 16) | (pg << 8) | (pb);
|
||||
}
|
||||
|
||||
static inline uint32_t combine_opacity(const plutovg_color_t* color, double opacity)
|
||||
{
|
||||
uint32_t a = (uint8_t)(color->a * opacity * 255);
|
||||
uint32_t r = (uint8_t)(color->r * 255);
|
||||
uint32_t g = (uint8_t)(color->g * 255);
|
||||
uint32_t b = (uint8_t)(color->b * 255);
|
||||
|
||||
return (a << 24) | (r << 16) | (g << 8) | (b);
|
||||
}
|
||||
|
||||
static inline uint32_t premultiply_pixel(uint32_t color)
|
||||
{
|
||||
uint32_t a = plutovg_alpha(color);
|
||||
uint32_t r = plutovg_red(color);
|
||||
uint32_t g = plutovg_green(color);
|
||||
uint32_t b = plutovg_blue(color);
|
||||
|
||||
uint32_t pr = (r * a) / 255;
|
||||
uint32_t pg = (g * a) / 255;
|
||||
uint32_t pb = (b * a) / 255;
|
||||
return (a << 24) | (pr << 16) | (pg << 8) | (pb);
|
||||
}
|
||||
|
||||
static inline uint32_t interpolate_pixel(uint32_t x, uint32_t a, uint32_t y, uint32_t b)
|
||||
{
|
||||
uint32_t t = (x & 0xff00ff) * a + (y & 0xff00ff) * b;
|
||||
t = (t + ((t >> 8) & 0xff00ff) + 0x800080) >> 8;
|
||||
t &= 0xff00ff;
|
||||
x = ((x >> 8) & 0xff00ff) * a + ((y >> 8) & 0xff00ff) * b;
|
||||
x = (x + ((x >> 8) & 0xff00ff) + 0x800080);
|
||||
x &= 0xff00ff00;
|
||||
x |= t;
|
||||
return x;
|
||||
}
|
||||
|
||||
static inline uint32_t BYTE_MUL(uint32_t x, uint32_t a)
|
||||
{
|
||||
uint32_t t = (x & 0xff00ff) * a;
|
||||
t = (t + ((t >> 8) & 0xff00ff) + 0x800080) >> 8;
|
||||
t &= 0xff00ff;
|
||||
x = ((x >> 8) & 0xff00ff) * a;
|
||||
x = (x + ((x >> 8) & 0xff00ff) + 0x800080);
|
||||
x &= 0xff00ff00;
|
||||
x |= t;
|
||||
return x;
|
||||
}
|
||||
|
||||
static inline void memfill32(uint32_t* dest, uint32_t value, int length)
|
||||
{
|
||||
for(int i = 0;i < length;i++)
|
||||
dest[i] = value;
|
||||
}
|
||||
|
||||
static inline int gradient_clamp(const gradient_data_t* gradient, int ipos)
|
||||
{
|
||||
if(gradient->spread == plutovg_spread_method_repeat)
|
||||
{
|
||||
ipos = ipos % COLOR_TABLE_SIZE;
|
||||
ipos = ipos < 0 ? COLOR_TABLE_SIZE + ipos : ipos;
|
||||
}
|
||||
else if(gradient->spread == plutovg_spread_method_reflect)
|
||||
{
|
||||
const int limit = COLOR_TABLE_SIZE * 2;
|
||||
ipos = ipos % limit;
|
||||
ipos = ipos < 0 ? limit + ipos : ipos;
|
||||
ipos = ipos >= COLOR_TABLE_SIZE ? limit - 1 - ipos : ipos;
|
||||
}
|
||||
else
|
||||
{
|
||||
if(ipos < 0)
|
||||
ipos = 0;
|
||||
else if(ipos >= COLOR_TABLE_SIZE)
|
||||
ipos = COLOR_TABLE_SIZE - 1;
|
||||
}
|
||||
|
||||
return ipos;
|
||||
}
|
||||
|
||||
#define FIXPT_BITS 8
|
||||
#define FIXPT_SIZE (1 << FIXPT_BITS)
|
||||
static inline uint32_t gradient_pixel_fixed(const gradient_data_t* gradient, int fixed_pos)
|
||||
{
|
||||
int ipos = (fixed_pos + (FIXPT_SIZE / 2)) >> FIXPT_BITS;
|
||||
return gradient->colortable[gradient_clamp(gradient, ipos)];
|
||||
}
|
||||
|
||||
static inline uint32_t gradient_pixel(const gradient_data_t* gradient, double pos)
|
||||
{
|
||||
int ipos = (int)(pos * (COLOR_TABLE_SIZE - 1) + 0.5);
|
||||
return gradient->colortable[gradient_clamp(gradient, ipos)];
|
||||
}
|
||||
|
||||
static void fetch_linear_gradient(uint32_t* buffer, const linear_gradient_values_t* v, const gradient_data_t* gradient, int y, int x, int length)
|
||||
{
|
||||
double t, inc;
|
||||
double rx = 0, ry = 0;
|
||||
|
||||
if(v->l == 0.0)
|
||||
{
|
||||
t = inc = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
rx = gradient->matrix.m01 * (y + 0.5) + gradient->matrix.m00 * (x + 0.5) + gradient->matrix.m02;
|
||||
ry = gradient->matrix.m11 * (y + 0.5) + gradient->matrix.m10 * (x + 0.5) + gradient->matrix.m12;
|
||||
t = v->dx * rx + v->dy * ry + v->off;
|
||||
inc = v->dx * gradient->matrix.m00 + v->dy * gradient->matrix.m10;
|
||||
t *= (COLOR_TABLE_SIZE - 1);
|
||||
inc *= (COLOR_TABLE_SIZE - 1);
|
||||
}
|
||||
|
||||
const uint32_t* end = buffer + length;
|
||||
if(inc > -1e-5 && inc < 1e-5)
|
||||
{
|
||||
memfill32(buffer, gradient_pixel_fixed(gradient, (int)(t * FIXPT_SIZE)), length);
|
||||
}
|
||||
else
|
||||
{
|
||||
if(t + inc * length < (double)(INT_MAX >> (FIXPT_BITS + 1)) && t + inc * length > (double)(INT_MIN >> (FIXPT_BITS + 1)))
|
||||
{
|
||||
int t_fixed = (int)(t * FIXPT_SIZE);
|
||||
int inc_fixed = (int)(inc * FIXPT_SIZE);
|
||||
while(buffer < end)
|
||||
{
|
||||
*buffer = gradient_pixel_fixed(gradient, t_fixed);
|
||||
t_fixed += inc_fixed;
|
||||
++buffer;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
while(buffer < end)
|
||||
{
|
||||
*buffer = gradient_pixel(gradient, t / COLOR_TABLE_SIZE);
|
||||
t += inc;
|
||||
++buffer;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void fetch_radial_gradient(uint32_t* buffer, const radial_gradient_values_t* v, const gradient_data_t* gradient, int y, int x, int length)
|
||||
{
|
||||
if(v->a == 0.0)
|
||||
{
|
||||
memfill32(buffer, 0, length);
|
||||
return;
|
||||
}
|
||||
|
||||
double rx = gradient->matrix.m01 * (y + 0.5) + gradient->matrix.m02 + gradient->matrix.m00 * (x + 0.5);
|
||||
double ry = gradient->matrix.m11 * (y + 0.5) + gradient->matrix.m12 + gradient->matrix.m10 * (x + 0.5);
|
||||
rx -= gradient->radial.fx;
|
||||
ry -= gradient->radial.fy;
|
||||
|
||||
double inv_a = 1.0 / (2.0 * v->a);
|
||||
double delta_rx = gradient->matrix.m00;
|
||||
double delta_ry = gradient->matrix.m10;
|
||||
|
||||
double b = 2 * (v->dr * gradient->radial.fr + rx * v->dx + ry * v->dy);
|
||||
double delta_b = 2 * (delta_rx * v->dx + delta_ry * v->dy);
|
||||
double b_delta_b = 2 * b * delta_b;
|
||||
double delta_b_delta_b = 2 * delta_b * delta_b;
|
||||
|
||||
double bb = b * b;
|
||||
double delta_bb = delta_b * delta_b;
|
||||
|
||||
b *= inv_a;
|
||||
delta_b *= inv_a;
|
||||
|
||||
double rxrxryry = rx * rx + ry * ry;
|
||||
double delta_rxrxryry = delta_rx * delta_rx + delta_ry * delta_ry;
|
||||
double rx_plus_ry = 2 * (rx * delta_rx + ry * delta_ry);
|
||||
double delta_rx_plus_ry = 2 * delta_rxrxryry;
|
||||
|
||||
inv_a *= inv_a;
|
||||
|
||||
double det = (bb - 4 * v->a * (v->sqrfr - rxrxryry)) * inv_a;
|
||||
double delta_det = (b_delta_b + delta_bb + 4 * v->a * (rx_plus_ry + delta_rxrxryry)) * inv_a;
|
||||
double delta_delta_det = (delta_b_delta_b + 4 * v->a * delta_rx_plus_ry) * inv_a;
|
||||
|
||||
const uint32_t* end = buffer + length;
|
||||
if(v->extended)
|
||||
{
|
||||
while(buffer < end)
|
||||
{
|
||||
uint32_t result = 0;
|
||||
if(det >= 0)
|
||||
{
|
||||
double w = sqrt(det) - b;
|
||||
if(gradient->radial.fr + v->dr * w >= 0)
|
||||
result = gradient_pixel(gradient, w);
|
||||
}
|
||||
|
||||
*buffer = result;
|
||||
det += delta_det;
|
||||
delta_det += delta_delta_det;
|
||||
b += delta_b;
|
||||
++buffer;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
while(buffer < end)
|
||||
{
|
||||
*buffer++ = gradient_pixel(gradient, sqrt(det) - b);
|
||||
det += delta_det;
|
||||
delta_det += delta_delta_det;
|
||||
b += delta_b;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void composition_solid_source(uint32_t* dest, int length, uint32_t color, uint32_t const_alpha)
|
||||
{
|
||||
if(const_alpha == 255)
|
||||
{
|
||||
memfill32(dest, color, length);
|
||||
}
|
||||
else
|
||||
{
|
||||
uint32_t ialpha = 255 - const_alpha;
|
||||
color = BYTE_MUL(color, const_alpha);
|
||||
for(int i = 0;i < length;i++)
|
||||
dest[i] = color + BYTE_MUL(dest[i], ialpha);
|
||||
}
|
||||
}
|
||||
|
||||
static void composition_solid_source_over(uint32_t* dest, int length, uint32_t color, uint32_t const_alpha)
|
||||
{
|
||||
if(const_alpha != 255) color = BYTE_MUL(color, const_alpha);
|
||||
uint32_t ialpha = 255 - plutovg_alpha(color);
|
||||
for(int i = 0;i < length;i++)
|
||||
dest[i] = color + BYTE_MUL(dest[i], ialpha);
|
||||
}
|
||||
|
||||
static void composition_solid_destination_in(uint32_t* dest, int length, uint32_t color, uint32_t const_alpha)
|
||||
{
|
||||
uint32_t a = plutovg_alpha(color);
|
||||
if(const_alpha != 255) a = BYTE_MUL(a, const_alpha) + 255 - const_alpha;
|
||||
for(int i = 0;i < length;i++)
|
||||
dest[i] = BYTE_MUL(dest[i], a);
|
||||
}
|
||||
|
||||
static void composition_solid_destination_out(uint32_t* dest, int length, uint32_t color, uint32_t const_alpha)
|
||||
{
|
||||
uint32_t a = plutovg_alpha(~color);
|
||||
if(const_alpha != 255) a = BYTE_MUL(a, const_alpha) + 255 - const_alpha;
|
||||
for(int i = 0; i < length;i++)
|
||||
dest[i] = BYTE_MUL(dest[i], a);
|
||||
}
|
||||
|
||||
static void composition_source(uint32_t* dest, int length, const uint32_t* src, uint32_t const_alpha)
|
||||
{
|
||||
if(const_alpha == 255)
|
||||
{
|
||||
memcpy(dest, src, (size_t)(length) * sizeof(uint32_t));
|
||||
}
|
||||
else
|
||||
{
|
||||
uint32_t ialpha = 255 - const_alpha;
|
||||
for(int i = 0;i < length;i++)
|
||||
dest[i] = interpolate_pixel(src[i], const_alpha, dest[i], ialpha);
|
||||
}
|
||||
}
|
||||
|
||||
static void composition_source_over(uint32_t* dest, int length, const uint32_t* src, uint32_t const_alpha)
|
||||
{
|
||||
uint32_t s, sia;
|
||||
if(const_alpha == 255)
|
||||
{
|
||||
for(int i = 0;i < length;i++)
|
||||
{
|
||||
s = src[i];
|
||||
if(s >= 0xff000000)
|
||||
dest[i] = s;
|
||||
else if(s != 0)
|
||||
{
|
||||
sia = plutovg_alpha(~s);
|
||||
dest[i] = s + BYTE_MUL(dest[i], sia);
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
for(int i = 0;i < length;i++)
|
||||
{
|
||||
s = BYTE_MUL(src[i], const_alpha);
|
||||
sia = plutovg_alpha(~s);
|
||||
dest[i] = s + BYTE_MUL(dest[i], sia);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void composition_destination_in(uint32_t* dest, int length, const uint32_t* src, uint32_t const_alpha)
|
||||
{
|
||||
if(const_alpha == 255)
|
||||
{
|
||||
for(int i = 0; i < length;i++)
|
||||
dest[i] = BYTE_MUL(dest[i], plutovg_alpha(src[i]));
|
||||
}
|
||||
else
|
||||
{
|
||||
uint32_t cia = 255 - const_alpha;
|
||||
uint32_t a;
|
||||
for(int i = 0;i < length;i++)
|
||||
{
|
||||
a = BYTE_MUL(plutovg_alpha(src[i]), const_alpha) + cia;
|
||||
dest[i] = BYTE_MUL(dest[i], a);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static void composition_destination_out(uint32_t* dest, int length, const uint32_t* src, uint32_t const_alpha)
|
||||
{
|
||||
if(const_alpha == 255)
|
||||
{
|
||||
for(int i = 0;i < length;i++)
|
||||
dest[i] = BYTE_MUL(dest[i], plutovg_alpha(~src[i]));
|
||||
}
|
||||
else
|
||||
{
|
||||
uint32_t cia = 255 - const_alpha;
|
||||
uint32_t sia;
|
||||
for(int i = 0;i < length;i++)
|
||||
{
|
||||
sia = BYTE_MUL(plutovg_alpha(~src[i]), const_alpha) + cia;
|
||||
dest[i] = BYTE_MUL(dest[i], sia);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
typedef void(*composition_solid_function_t)(uint32_t* dest, int length, uint32_t color, uint32_t const_alpha);
|
||||
typedef void(*composition_function_t)(uint32_t* dest, int length, const uint32_t* src, uint32_t const_alpha);
|
||||
|
||||
static const composition_solid_function_t composition_solid_map[] = {
|
||||
composition_solid_source,
|
||||
composition_solid_source_over,
|
||||
composition_solid_destination_in,
|
||||
composition_solid_destination_out
|
||||
};
|
||||
|
||||
static const composition_function_t composition_map[] = {
|
||||
composition_source,
|
||||
composition_source_over,
|
||||
composition_destination_in,
|
||||
composition_destination_out
|
||||
};
|
||||
|
||||
static void blend_solid(plutovg_surface_t* surface, plutovg_operator_t op, const plutovg_rle_t* rle, uint32_t solid)
|
||||
{
|
||||
composition_solid_function_t func = composition_solid_map[op];
|
||||
int count = rle->spans.size;
|
||||
const plutovg_span_t* spans = rle->spans.data;
|
||||
while(count--)
|
||||
{
|
||||
uint32_t* target = (uint32_t*)(surface->data + spans->y * surface->stride) + spans->x;
|
||||
func(target, spans->len, solid, spans->coverage);
|
||||
++spans;
|
||||
}
|
||||
}
|
||||
|
||||
#define BUFFER_SIZE 1024
|
||||
static void blend_linear_gradient(plutovg_surface_t* surface, plutovg_operator_t op, const plutovg_rle_t* rle, const gradient_data_t* gradient)
|
||||
{
|
||||
composition_function_t func = composition_map[op];
|
||||
unsigned int buffer[BUFFER_SIZE];
|
||||
|
||||
linear_gradient_values_t v;
|
||||
v.dx = gradient->linear.x2 - gradient->linear.x1;
|
||||
v.dy = gradient->linear.y2 - gradient->linear.y1;
|
||||
v.l = v.dx * v.dx + v.dy * v.dy;
|
||||
v.off = 0.0;
|
||||
if(v.l != 0.0)
|
||||
{
|
||||
v.dx /= v.l;
|
||||
v.dy /= v.l;
|
||||
v.off = -v.dx * gradient->linear.x1 - v.dy * gradient->linear.y1;
|
||||
}
|
||||
|
||||
int count = rle->spans.size;
|
||||
const plutovg_span_t* spans = rle->spans.data;
|
||||
while(count--)
|
||||
{
|
||||
int length = spans->len;
|
||||
int x = spans->x;
|
||||
while(length)
|
||||
{
|
||||
int l = MIN(length, BUFFER_SIZE);
|
||||
fetch_linear_gradient(buffer, &v, gradient, spans->y, x, l);
|
||||
uint32_t* target = (uint32_t*)(surface->data + spans->y * surface->stride) + x;
|
||||
func(target, l, buffer, spans->coverage);
|
||||
x += l;
|
||||
length -= l;
|
||||
}
|
||||
|
||||
++spans;
|
||||
}
|
||||
}
|
||||
|
||||
static void blend_radial_gradient(plutovg_surface_t* surface, plutovg_operator_t op, const plutovg_rle_t* rle, const gradient_data_t* gradient)
|
||||
{
|
||||
composition_function_t func = composition_map[op];
|
||||
unsigned int buffer[BUFFER_SIZE];
|
||||
|
||||
radial_gradient_values_t v;
|
||||
v.dx = gradient->radial.cx - gradient->radial.fx;
|
||||
v.dy = gradient->radial.cy - gradient->radial.fy;
|
||||
v.dr = gradient->radial.cr - gradient->radial.fr;
|
||||
v.sqrfr = gradient->radial.fr * gradient->radial.fr;
|
||||
v.a = v.dr * v.dr - v.dx * v.dx - v.dy * v.dy;
|
||||
v.inv2a = 1.0 / (2.0 * v.a);
|
||||
v.extended = gradient->radial.fr != 0.0 || v.a <= 0.0;
|
||||
|
||||
int count = rle->spans.size;
|
||||
const plutovg_span_t* spans = rle->spans.data;
|
||||
while(count--)
|
||||
{
|
||||
int length = spans->len;
|
||||
int x = spans->x;
|
||||
while(length)
|
||||
{
|
||||
int l = MIN(length, BUFFER_SIZE);
|
||||
fetch_radial_gradient(buffer, &v, gradient, spans->y, x, l);
|
||||
uint32_t* target = (uint32_t*)(surface->data + spans->y * surface->stride) + x;
|
||||
func(target, l, buffer, spans->coverage);
|
||||
x += l;
|
||||
length -= l;
|
||||
}
|
||||
|
||||
++spans;
|
||||
}
|
||||
}
|
||||
|
||||
#define FIXED_SCALE (1 << 16)
|
||||
static void blend_transformed_argb(plutovg_surface_t* surface, plutovg_operator_t op, const plutovg_rle_t* rle, const texture_data_t* texture)
|
||||
{
|
||||
composition_function_t func = composition_map[op];
|
||||
uint32_t buffer[BUFFER_SIZE];
|
||||
|
||||
int image_width = texture->width;
|
||||
int image_height = texture->height;
|
||||
|
||||
int fdx = (int)(texture->matrix.m00 * FIXED_SCALE);
|
||||
int fdy = (int)(texture->matrix.m10 * FIXED_SCALE);
|
||||
|
||||
int count = rle->spans.size;
|
||||
const plutovg_span_t* spans = rle->spans.data;
|
||||
while(count--)
|
||||
{
|
||||
uint32_t* target = (uint32_t*)(surface->data + spans->y * surface->stride) + spans->x;
|
||||
|
||||
const double cx = spans->x + 0.5;
|
||||
const double cy = spans->y + 0.5;
|
||||
|
||||
int x = (int)((texture->matrix.m01 * cy + texture->matrix.m00 * cx + texture->matrix.m02) * FIXED_SCALE);
|
||||
int y = (int)((texture->matrix.m11 * cy + texture->matrix.m10 * cx + texture->matrix.m12) * FIXED_SCALE);
|
||||
|
||||
int length = spans->len;
|
||||
const int coverage = (spans->coverage * texture->const_alpha) >> 8;
|
||||
while(length)
|
||||
{
|
||||
int l = MIN(length, BUFFER_SIZE);
|
||||
const uint32_t* end = buffer + l;
|
||||
uint32_t* b = buffer;
|
||||
while(b < end)
|
||||
{
|
||||
int px = CLAMP(x >> 16, 0, image_width - 1);
|
||||
int py = CLAMP(y >> 16, 0, image_height - 1);
|
||||
*b = ((const uint32_t*)(texture->data + py * texture->stride))[px];
|
||||
|
||||
x += fdx;
|
||||
y += fdy;
|
||||
++b;
|
||||
}
|
||||
|
||||
func(target, l, buffer, coverage);
|
||||
target += l;
|
||||
length -= l;
|
||||
}
|
||||
|
||||
++spans;
|
||||
}
|
||||
}
|
||||
|
||||
static void blend_untransformed_argb(plutovg_surface_t* surface, plutovg_operator_t op, const plutovg_rle_t* rle, const texture_data_t* texture)
|
||||
{
|
||||
composition_function_t func = composition_map[op];
|
||||
|
||||
const int image_width = texture->width;
|
||||
const int image_height = texture->height;
|
||||
|
||||
int xoff = (int)(texture->matrix.m02);
|
||||
int yoff = (int)(texture->matrix.m12);
|
||||
|
||||
int count = rle->spans.size;
|
||||
const plutovg_span_t* spans = rle->spans.data;
|
||||
while(count--)
|
||||
{
|
||||
int x = spans->x;
|
||||
int length = spans->len;
|
||||
int sx = xoff + x;
|
||||
int sy = yoff + spans->y;
|
||||
if(sy >= 0 && sy < image_height && sx < image_width)
|
||||
{
|
||||
if(sx < 0)
|
||||
{
|
||||
x -= sx;
|
||||
length += sx;
|
||||
sx = 0;
|
||||
}
|
||||
|
||||
if(sx + length > image_width)
|
||||
length = image_width - sx;
|
||||
|
||||
if(length > 0)
|
||||
{
|
||||
const int coverage = (spans->coverage * texture->const_alpha) >> 8;
|
||||
const uint32_t* src = (const uint32_t*)(texture->data + sy * texture->stride) + sx;
|
||||
uint32_t* dest = (uint32_t*)(surface->data + spans->y * surface->stride) + x;
|
||||
func(dest, length, src, coverage);
|
||||
}
|
||||
}
|
||||
|
||||
++spans;
|
||||
}
|
||||
}
|
||||
|
||||
static void blend_untransformed_tiled_argb(plutovg_surface_t* surface, plutovg_operator_t op, const plutovg_rle_t* rle, const texture_data_t* texture)
|
||||
{
|
||||
composition_function_t func = composition_map[op];
|
||||
|
||||
int image_width = texture->width;
|
||||
int image_height = texture->height;
|
||||
|
||||
int xoff = (int)(texture->matrix.m02) % image_width;
|
||||
int yoff = (int)(texture->matrix.m12) % image_height;
|
||||
|
||||
if(xoff < 0)
|
||||
xoff += image_width;
|
||||
if(yoff < 0)
|
||||
yoff += image_height;
|
||||
|
||||
int count = rle->spans.size;
|
||||
const plutovg_span_t* spans = rle->spans.data;
|
||||
while(count--)
|
||||
{
|
||||
int x = spans->x;
|
||||
int length = spans->len;
|
||||
int sx = (xoff + spans->x) % image_width;
|
||||
int sy = (spans->y + yoff) % image_height;
|
||||
if(sx < 0)
|
||||
sx += image_width;
|
||||
if(sy < 0)
|
||||
sy += image_height;
|
||||
|
||||
const int coverage = (spans->coverage * texture->const_alpha) >> 8;
|
||||
while(length)
|
||||
{
|
||||
int l = MIN(image_width - sx, length);
|
||||
if(BUFFER_SIZE < l)
|
||||
l = BUFFER_SIZE;
|
||||
const uint32_t* src = (const uint32_t*)(texture->data + sy * texture->stride) + sx;
|
||||
uint32_t* dest = (uint32_t*)(surface->data + spans->y * surface->stride) + x;
|
||||
func(dest, l, src, coverage);
|
||||
x += l;
|
||||
length -= l;
|
||||
sx = 0;
|
||||
}
|
||||
|
||||
++spans;
|
||||
}
|
||||
}
|
||||
|
||||
static void blend_transformed_tiled_argb(plutovg_surface_t* surface, plutovg_operator_t op, const plutovg_rle_t* rle, const texture_data_t* texture)
|
||||
{
|
||||
composition_function_t func = composition_map[op];
|
||||
uint32_t buffer[BUFFER_SIZE];
|
||||
|
||||
int image_width = texture->width;
|
||||
int image_height = texture->height;
|
||||
const int scanline_offset = texture->stride / 4;
|
||||
|
||||
int fdx = (int)(texture->matrix.m00 * FIXED_SCALE);
|
||||
int fdy = (int)(texture->matrix.m10 * FIXED_SCALE);
|
||||
|
||||
int count = rle->spans.size;
|
||||
const plutovg_span_t* spans = rle->spans.data;
|
||||
while(count--)
|
||||
{
|
||||
uint32_t* target = (uint32_t*)(surface->data + spans->y * surface->stride) + spans->x;
|
||||
const uint32_t* image_bits = (const uint32_t*)texture->data;
|
||||
|
||||
const double cx = spans->x + 0.5;
|
||||
const double cy = spans->y + 0.5;
|
||||
|
||||
int x = (int)((texture->matrix.m01 * cy + texture->matrix.m00 * cx + texture->matrix.m02) * FIXED_SCALE);
|
||||
int y = (int)((texture->matrix.m11 * cy + texture->matrix.m10 * cx + texture->matrix.m12) * FIXED_SCALE);
|
||||
|
||||
const int coverage = (spans->coverage * texture->const_alpha) >> 8;
|
||||
int length = spans->len;
|
||||
while(length)
|
||||
{
|
||||
int l = MIN(length, BUFFER_SIZE);
|
||||
const uint32_t* end = buffer + l;
|
||||
uint32_t* b = buffer;
|
||||
int px16 = x % (image_width << 16);
|
||||
int py16 = y % (image_height << 16);
|
||||
int px_delta = fdx % (image_width << 16);
|
||||
int py_delta = fdy % (image_height << 16);
|
||||
while(b < end)
|
||||
{
|
||||
if(px16 < 0) px16 += image_width << 16;
|
||||
if(py16 < 0) py16 += image_height << 16;
|
||||
int px = px16 >> 16;
|
||||
int py = py16 >> 16;
|
||||
int y_offset = py * scanline_offset;
|
||||
|
||||
*b = image_bits[y_offset + px];
|
||||
x += fdx;
|
||||
y += fdy;
|
||||
px16 += px_delta;
|
||||
if(px16 >= image_width << 16)
|
||||
px16 -= image_width << 16;
|
||||
py16 += py_delta;
|
||||
if(py16 >= image_height << 16)
|
||||
py16 -= image_height << 16;
|
||||
++b;
|
||||
}
|
||||
|
||||
func(target, l, buffer, coverage);
|
||||
target += l;
|
||||
length -= l;
|
||||
}
|
||||
|
||||
++spans;
|
||||
}
|
||||
}
|
||||
|
||||
void plutovg_blend_color(plutovg_t* pluto, const plutovg_rle_t* rle, const plutovg_color_t* color)
|
||||
{
|
||||
if(color == NULL)
|
||||
return;
|
||||
|
||||
plutovg_state_t* state = pluto->state;
|
||||
uint32_t solid = premultiply_color(color, state->opacity);
|
||||
|
||||
uint32_t alpha = plutovg_alpha(solid);
|
||||
if(alpha == 255 && state->op == plutovg_operator_src_over)
|
||||
blend_solid(pluto->surface, plutovg_operator_src, rle, solid);
|
||||
else
|
||||
blend_solid(pluto->surface, state->op, rle, solid);
|
||||
}
|
||||
|
||||
void plutovg_blend_gradient(plutovg_t* pluto, const plutovg_rle_t* rle, const plutovg_gradient_t* gradient)
|
||||
{
|
||||
if(gradient == NULL || gradient->stops.size == 0)
|
||||
return;
|
||||
|
||||
plutovg_state_t* state = pluto->state;
|
||||
gradient_data_t data;
|
||||
int i, pos = 0, nstop = gradient->stops.size;
|
||||
const plutovg_gradient_stop_t *curr, *next, *start, *last;
|
||||
uint32_t curr_color, next_color, last_color;
|
||||
uint32_t dist, idist;
|
||||
double delta, t, incr, fpos;
|
||||
double opacity = state->opacity * gradient->opacity;
|
||||
|
||||
start = gradient->stops.data;
|
||||
curr = start;
|
||||
curr_color = combine_opacity(&curr->color, opacity);
|
||||
|
||||
data.colortable[pos] = premultiply_pixel(curr_color);
|
||||
++pos;
|
||||
incr = 1.0 / COLOR_TABLE_SIZE;
|
||||
fpos = 1.5 * incr;
|
||||
|
||||
while(fpos <= curr->offset)
|
||||
{
|
||||
data.colortable[pos] = data.colortable[pos - 1];
|
||||
++pos;
|
||||
fpos += incr;
|
||||
}
|
||||
|
||||
for(i = 0;i < nstop - 1;i++)
|
||||
{
|
||||
curr = (start + i);
|
||||
next = (start + i + 1);
|
||||
delta = 1.0 / (next->offset - curr->offset);
|
||||
next_color = combine_opacity(&next->color, opacity);
|
||||
while(fpos < next->offset && pos < COLOR_TABLE_SIZE)
|
||||
{
|
||||
t = (fpos - curr->offset) * delta;
|
||||
dist = (uint32_t)(255 * t);
|
||||
idist = 255 - dist;
|
||||
data.colortable[pos] = premultiply_pixel(interpolate_pixel(curr_color, idist, next_color, dist));
|
||||
++pos;
|
||||
fpos += incr;
|
||||
}
|
||||
|
||||
curr_color = next_color;
|
||||
}
|
||||
|
||||
last = start + nstop - 1;
|
||||
last_color = premultiply_color(&last->color, opacity);
|
||||
for(;pos < COLOR_TABLE_SIZE;++pos)
|
||||
data.colortable[pos] = last_color;
|
||||
|
||||
data.spread = gradient->spread;
|
||||
data.matrix = gradient->matrix;
|
||||
plutovg_matrix_multiply(&data.matrix, &data.matrix, &state->matrix);
|
||||
plutovg_matrix_invert(&data.matrix);
|
||||
|
||||
if(gradient->type == plutovg_gradient_type_linear)
|
||||
{
|
||||
data.linear.x1 = gradient->values[0];
|
||||
data.linear.y1 = gradient->values[1];
|
||||
data.linear.x2 = gradient->values[2];
|
||||
data.linear.y2 = gradient->values[3];
|
||||
blend_linear_gradient(pluto->surface, state->op, rle, &data);
|
||||
}
|
||||
else
|
||||
{
|
||||
data.radial.cx = gradient->values[0];
|
||||
data.radial.cy = gradient->values[1];
|
||||
data.radial.cr = gradient->values[2];
|
||||
data.radial.fx = gradient->values[3];
|
||||
data.radial.fy = gradient->values[4];
|
||||
data.radial.fr = gradient->values[5];
|
||||
blend_radial_gradient(pluto->surface, state->op, rle, &data);
|
||||
}
|
||||
}
|
||||
|
||||
void plutovg_blend_texture(plutovg_t* pluto, const plutovg_rle_t* rle, const plutovg_texture_t* texture)
|
||||
{
|
||||
if(texture == NULL)
|
||||
return;
|
||||
|
||||
plutovg_state_t* state = pluto->state;
|
||||
texture_data_t data;
|
||||
data.data = texture->surface->data;
|
||||
data.width = texture->surface->width;
|
||||
data.height = texture->surface->height;
|
||||
data.stride = texture->surface->stride;
|
||||
data.const_alpha = (int)(state->opacity * texture->opacity * 256.0);
|
||||
data.matrix = texture->matrix;
|
||||
|
||||
plutovg_matrix_multiply(&data.matrix, &data.matrix, &state->matrix);
|
||||
plutovg_matrix_invert(&data.matrix);
|
||||
|
||||
const plutovg_matrix_t* matrix = &data.matrix;
|
||||
int translating = (matrix->m00 == 1.0 && matrix->m10 == 0.0 && matrix->m01 == 0.0 && matrix->m11 == 1.0);
|
||||
if(translating)
|
||||
{
|
||||
if(texture->type == plutovg_texture_type_plain)
|
||||
blend_untransformed_argb(pluto->surface, state->op, rle, &data);
|
||||
else
|
||||
blend_untransformed_tiled_argb(pluto->surface, state->op, rle, &data);
|
||||
}
|
||||
else
|
||||
{
|
||||
if(texture->type == plutovg_texture_type_plain)
|
||||
blend_transformed_argb(pluto->surface, state->op, rle, &data);
|
||||
else
|
||||
blend_transformed_tiled_argb(pluto->surface, state->op, rle, &data);
|
||||
}
|
||||
}
|
||||
|
||||
void plutovg_blend(plutovg_t* pluto, const plutovg_rle_t* rle)
|
||||
{
|
||||
if(rle == NULL || rle->spans.size == 0)
|
||||
return;
|
||||
|
||||
plutovg_paint_t* source = pluto->state->source;
|
||||
if(source->type == plutovg_paint_type_color)
|
||||
plutovg_blend_color(pluto, rle, source->color);
|
||||
else if(source->type == plutovg_paint_type_gradient)
|
||||
plutovg_blend_gradient(pluto, rle, source->gradient);
|
||||
else
|
||||
plutovg_blend_texture(pluto, rle, source->texture);
|
||||
}
|
||||
@@ -0,0 +1,111 @@
|
||||
#include "plutovg-private.h"
|
||||
|
||||
#include <math.h>
|
||||
|
||||
plutovg_dash_t* plutovg_dash_create(double offset, const double* data, int size)
|
||||
{
|
||||
if(data == NULL || size == 0)
|
||||
return NULL;
|
||||
|
||||
plutovg_dash_t* dash = malloc(sizeof(plutovg_dash_t));
|
||||
dash->offset = offset;
|
||||
dash->data = malloc((size_t)size * sizeof(double));
|
||||
dash->size = size;
|
||||
memcpy(dash->data, data, (size_t)size * sizeof(double));
|
||||
return dash;
|
||||
}
|
||||
|
||||
plutovg_dash_t* plutovg_dash_clone(const plutovg_dash_t* dash)
|
||||
{
|
||||
if(dash == NULL)
|
||||
return NULL;
|
||||
|
||||
return plutovg_dash_create(dash->offset, dash->data, dash->size);
|
||||
}
|
||||
|
||||
void plutovg_dash_destroy(plutovg_dash_t* dash)
|
||||
{
|
||||
if(dash == NULL)
|
||||
return;
|
||||
|
||||
free(dash->data);
|
||||
free(dash);
|
||||
}
|
||||
|
||||
plutovg_path_t* plutovg_dash_path(const plutovg_dash_t* dash, const plutovg_path_t* path)
|
||||
{
|
||||
plutovg_path_t* flat = plutovg_path_clone_flat(path);
|
||||
plutovg_path_t* result = plutovg_path_create();
|
||||
|
||||
plutovg_array_ensure(result->elements, flat->elements.size);
|
||||
plutovg_array_ensure(result->points, flat->points.size);
|
||||
|
||||
int toggle = 1;
|
||||
int offset = 0;
|
||||
double phase = dash->offset;
|
||||
while(phase >= dash->data[offset])
|
||||
{
|
||||
toggle = !toggle;
|
||||
phase -= dash->data[offset];
|
||||
offset += 1;
|
||||
if(offset == dash->size) offset = 0;
|
||||
}
|
||||
|
||||
plutovg_path_element_t* elements = flat->elements.data;
|
||||
plutovg_path_element_t* end = elements + flat->elements.size;
|
||||
plutovg_point_t* points = flat->points.data;
|
||||
while(elements < end)
|
||||
{
|
||||
int itoggle = toggle;
|
||||
int ioffset = offset;
|
||||
double iphase = phase;
|
||||
|
||||
double x0 = points->x;
|
||||
double y0 = points->y;
|
||||
|
||||
if(itoggle)
|
||||
plutovg_path_move_to(result, x0, y0);
|
||||
|
||||
++elements;
|
||||
++points;
|
||||
|
||||
while(elements < end && *elements == plutovg_path_element_line_to)
|
||||
{
|
||||
double dx = points->x - x0;
|
||||
double dy = points->y - y0;
|
||||
double dist0 = sqrt(dx*dx + dy*dy);
|
||||
double dist1 = 0;
|
||||
while(dist0 - dist1 > dash->data[ioffset] - iphase)
|
||||
{
|
||||
dist1 += dash->data[ioffset] - iphase;
|
||||
double a = dist1 / dist0;
|
||||
double x = x0 + a * dx;
|
||||
double y = y0 + a * dy;
|
||||
|
||||
if(itoggle)
|
||||
plutovg_path_line_to(result, x, y);
|
||||
else
|
||||
plutovg_path_move_to(result, x, y);
|
||||
|
||||
itoggle = !itoggle;
|
||||
iphase = 0;
|
||||
ioffset += 1;
|
||||
if(ioffset == dash->size) ioffset = 0;
|
||||
}
|
||||
|
||||
iphase += dist0 - dist1;
|
||||
|
||||
x0 = points->x;
|
||||
y0 = points->y;
|
||||
|
||||
if(itoggle)
|
||||
plutovg_path_line_to(result, x0, y0);
|
||||
|
||||
++elements;
|
||||
++points;
|
||||
}
|
||||
}
|
||||
|
||||
plutovg_path_destroy(flat);
|
||||
return result;
|
||||
}
|
||||
@@ -0,0 +1,564 @@
|
||||
#define STB_TRUETYPE_IMPLEMENTATION
|
||||
#include "plutovg-private.h"
|
||||
#include "stb_truetype.h"
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
struct plutovg_font_data_t {
|
||||
int ref;
|
||||
const unsigned char* data;
|
||||
int datasize;
|
||||
int owndata;
|
||||
};
|
||||
|
||||
plutovg_font_data_t* plutovg_font_data_load_from_memory(const unsigned char* data, int datasize, int owndata)
|
||||
{
|
||||
plutovg_font_data_t* fontdata = malloc(sizeof(plutovg_font_data_t));
|
||||
if(fontdata)
|
||||
{
|
||||
fontdata->ref = 1;
|
||||
fontdata->data = data;
|
||||
fontdata->datasize = datasize;
|
||||
fontdata->owndata = owndata;
|
||||
}
|
||||
return fontdata;
|
||||
}
|
||||
|
||||
plutovg_font_data_t* plutovg_font_data_load_from_file(const char* filename)
|
||||
{
|
||||
FILE* fp = NULL;
|
||||
fopen_s(&fp, filename, "rb");
|
||||
if(fp == NULL)
|
||||
return NULL;
|
||||
|
||||
fseek(fp, 0, SEEK_END);
|
||||
size_t size = (size_t)ftell(fp);
|
||||
unsigned char* data = malloc(size);
|
||||
fseek(fp, 0, SEEK_SET);
|
||||
|
||||
fread(data, 1, size, fp);
|
||||
fclose(fp);
|
||||
|
||||
return plutovg_font_data_load_from_memory(data, (int)size, 1);
|
||||
}
|
||||
|
||||
plutovg_font_data_t* plutovg_font_data_reference(plutovg_font_data_t* data)
|
||||
{
|
||||
if(data == NULL)
|
||||
return NULL;
|
||||
|
||||
++data->ref;
|
||||
return data;
|
||||
}
|
||||
|
||||
void plutovg_font_data_destroy(plutovg_font_data_t* data)
|
||||
{
|
||||
if(data == NULL)
|
||||
return;
|
||||
|
||||
if(--data->ref == 0)
|
||||
{
|
||||
if(data->owndata)
|
||||
free((void*)(data->data));
|
||||
free(data);
|
||||
}
|
||||
}
|
||||
|
||||
int plutovg_font_data_get_reference_count(const plutovg_font_data_t* data)
|
||||
{
|
||||
if(data == NULL)
|
||||
return 0;
|
||||
|
||||
return data->ref;
|
||||
}
|
||||
|
||||
int plutovg_font_data_face_count(const plutovg_font_data_t* data)
|
||||
{
|
||||
return stbtt_GetNumberOfFonts(data->data);
|
||||
}
|
||||
|
||||
#define CACHE_SIZE 256
|
||||
typedef struct {
|
||||
int codepoint;
|
||||
int advance;
|
||||
int x1, y1, x2, y2;
|
||||
plutovg_path_t* path;
|
||||
} plutovg_glyph_t;
|
||||
|
||||
struct plutovg_font_face {
|
||||
int ref;
|
||||
int ascent, descent, linegap;
|
||||
int x1, y1, x2, y2;
|
||||
stbtt_fontinfo info;
|
||||
plutovg_font_data_t* data;
|
||||
plutovg_glyph_t cache[CACHE_SIZE];
|
||||
};
|
||||
|
||||
plutovg_font_face_t* plutovg_font_face_load_from_memory(const unsigned char* data, int datasize, int owndata)
|
||||
{
|
||||
plutovg_font_data_t* fontdata = plutovg_font_data_load_from_memory(data, datasize, owndata);
|
||||
plutovg_font_face_t* fontface = plutovg_font_face_load_from_data(fontdata, 0);
|
||||
plutovg_font_data_destroy(fontdata);
|
||||
return fontface;
|
||||
}
|
||||
|
||||
plutovg_font_face_t* plutovg_font_face_load_from_file(const char* filename)
|
||||
{
|
||||
plutovg_font_data_t* fontdata = plutovg_font_data_load_from_file(filename);
|
||||
plutovg_font_face_t* fontface = plutovg_font_face_load_from_data(fontdata, 0);
|
||||
plutovg_font_data_destroy(fontdata);
|
||||
return fontface;
|
||||
}
|
||||
|
||||
plutovg_font_face_t* plutovg_font_face_load_from_data(plutovg_font_data_t* data, int index)
|
||||
{
|
||||
if(data == NULL)
|
||||
return NULL;
|
||||
|
||||
stbtt_fontinfo info;
|
||||
if(!stbtt_InitFont(&info, data->data, index))
|
||||
return NULL;
|
||||
|
||||
plutovg_font_face_t* fontface = malloc(sizeof(plutovg_font_face_t));
|
||||
fontface->ref = 1;
|
||||
fontface->data = plutovg_font_data_reference(data);
|
||||
fontface->info = info;
|
||||
stbtt_GetFontVMetrics(&fontface->info, &fontface->ascent, &fontface->descent, &fontface->linegap);
|
||||
stbtt_GetFontBoundingBox(&fontface->info, &fontface->x1, &fontface->y1, &fontface->x2, &fontface->y2);
|
||||
memset(fontface->cache, 0, sizeof(fontface->cache));
|
||||
return fontface;
|
||||
}
|
||||
|
||||
plutovg_font_face_t* plutovg_font_face_reference(plutovg_font_face_t* face)
|
||||
{
|
||||
if(face == NULL)
|
||||
return NULL;
|
||||
|
||||
++face->ref;
|
||||
return face;
|
||||
}
|
||||
|
||||
void plutovg_font_face_destroy(plutovg_font_face_t* face)
|
||||
{
|
||||
if(face == NULL)
|
||||
return;
|
||||
|
||||
if(--face->ref == 0)
|
||||
{
|
||||
for(int i = 0;i < CACHE_SIZE;i++)
|
||||
{
|
||||
plutovg_glyph_t* glyph = &face->cache[i];
|
||||
plutovg_path_destroy(glyph->path);
|
||||
}
|
||||
|
||||
plutovg_font_data_destroy(face->data);
|
||||
free(face);
|
||||
}
|
||||
}
|
||||
|
||||
int plutovg_font_face_get_reference_count(const plutovg_font_face_t* face)
|
||||
{
|
||||
if(face == NULL)
|
||||
return 0;
|
||||
|
||||
return face->ref;
|
||||
}
|
||||
|
||||
plutovg_font_style_t plutovg_font_face_get_style(const plutovg_font_face_t* face)
|
||||
{
|
||||
(face);
|
||||
return plutovg_font_style_normal;
|
||||
}
|
||||
|
||||
const char* plutovg_font_face_get_family(const plutovg_font_face_t* face)
|
||||
{
|
||||
(face);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
static inline plutovg_glyph_t *find_glyph(const plutovg_font_face_t *face, int codepoint)
|
||||
{
|
||||
plutovg_glyph_t *glyph = (void *)(&face->cache[codepoint % CACHE_SIZE]);
|
||||
if(glyph->codepoint == codepoint)
|
||||
return glyph;
|
||||
|
||||
glyph->codepoint = codepoint;
|
||||
if(glyph->path == NULL)
|
||||
glyph->path = plutovg_path_create();
|
||||
else
|
||||
plutovg_path_clear(glyph->path);
|
||||
|
||||
int index = stbtt_FindGlyphIndex(&face->info, codepoint);
|
||||
stbtt_vertex *v;
|
||||
int num_vertices = stbtt_GetGlyphShape(&face->info, index, &v);
|
||||
for(int i = 0; i < num_vertices; i++)
|
||||
{
|
||||
switch(v[i].type) {
|
||||
case STBTT_vmove:
|
||||
plutovg_path_move_to(glyph->path, v[i].x, v[i].y);
|
||||
break;
|
||||
case STBTT_vline:
|
||||
plutovg_path_line_to(glyph->path, v[i].x, v[i].y);
|
||||
break;
|
||||
case STBTT_vcurve:
|
||||
plutovg_path_quad_to(glyph->path, v[i].cx, v[i].cy, v[i].x, v[i].y);
|
||||
break;
|
||||
case STBTT_vcubic:
|
||||
plutovg_path_cubic_to(glyph->path, v[i].cx, v[i].cy, v[i].cx1, v[i].cy1, v[i].x, v[i].y);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
stbtt_FreeShape(&face->info, v);
|
||||
stbtt_GetGlyphHMetrics(&face->info, index, &glyph->advance, NULL);
|
||||
stbtt_GetGlyphBox(&face->info, index, &glyph->x1, &glyph->y1, &glyph->x2, &glyph->y2);
|
||||
return glyph;
|
||||
}
|
||||
|
||||
plutovg_path_t* plutovg_font_face_get_char_path(const plutovg_font_face_t* face, int ch)
|
||||
{
|
||||
plutovg_glyph_t* glyph = find_glyph(face, ch);
|
||||
return plutovg_path_reference(glyph->path);
|
||||
}
|
||||
|
||||
void plutovg_font_face_get_char_extents(const plutovg_font_face_t* face, int ch, plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_glyph_t* glyph = find_glyph(face, ch);
|
||||
plutovg_rect_init(rect, glyph->x1, glyph->y1, glyph->x2 - glyph->x1, glyph->y2 - glyph->y1);
|
||||
}
|
||||
|
||||
double plutovg_font_face_get_char_advance(const plutovg_font_face_t* face, int ch)
|
||||
{
|
||||
plutovg_glyph_t* glyph = find_glyph(face, ch);
|
||||
return glyph->advance;
|
||||
}
|
||||
|
||||
void plutovg_font_face_get_matrix(const plutovg_font_face_t* face, double size, plutovg_matrix_t* matrix)
|
||||
{
|
||||
double scale = plutovg_font_face_get_scale(face, size);
|
||||
plutovg_matrix_init_scale(matrix, scale, -scale);
|
||||
}
|
||||
|
||||
double plutovg_font_face_get_scale(const plutovg_font_face_t* face, double size)
|
||||
{
|
||||
return stbtt_ScaleForMappingEmToPixels(&face->info, (float)size);
|
||||
}
|
||||
|
||||
double plutovg_font_face_get_ascent(const plutovg_font_face_t* face)
|
||||
{
|
||||
return face->ascent;
|
||||
}
|
||||
|
||||
double plutovg_font_face_get_descent(const plutovg_font_face_t* face)
|
||||
{
|
||||
return face->descent;
|
||||
}
|
||||
|
||||
double plutovg_font_face_get_line_gap(const plutovg_font_face_t* face)
|
||||
{
|
||||
return face->linegap;
|
||||
}
|
||||
|
||||
double plutovg_font_face_get_leading(const plutovg_font_face_t* face)
|
||||
{
|
||||
return (face->ascent - face->descent + face->linegap);
|
||||
}
|
||||
|
||||
double plutovg_font_face_get_kerning(const plutovg_font_face_t* face, int ch1, int ch2)
|
||||
{
|
||||
return stbtt_GetCodepointKernAdvance(&face->info, ch1, ch2);
|
||||
}
|
||||
|
||||
void plutovg_font_face_get_extents(const plutovg_font_face_t* face, plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_rect_init(rect, face->x1, face->y1, face->x2 - face->x1, face->y2 - face->y1);
|
||||
}
|
||||
|
||||
struct plutovg_font {
|
||||
int ref;
|
||||
double size;
|
||||
plutovg_font_face_t* face;
|
||||
};
|
||||
|
||||
plutovg_font_t* plutovg_font_load_from_memory(const unsigned char* data, int datasize, int owndata, double size)
|
||||
{
|
||||
plutovg_font_face_t* fontface = plutovg_font_face_load_from_memory(data, datasize, owndata);
|
||||
plutovg_font_t* font = plutovg_font_load_from_face(fontface, size);
|
||||
plutovg_font_face_destroy(fontface);
|
||||
return font;
|
||||
}
|
||||
|
||||
plutovg_font_t* plutovg_font_load_from_file(const char* filename, double size)
|
||||
{
|
||||
plutovg_font_face_t* fontface = plutovg_font_face_load_from_file(filename);
|
||||
plutovg_font_t* font = plutovg_font_load_from_face(fontface, size);
|
||||
plutovg_font_face_destroy(fontface);
|
||||
return font;
|
||||
}
|
||||
|
||||
plutovg_font_t* plutovg_font_load_from_data(plutovg_font_data_t* data, int index, double size)
|
||||
{
|
||||
plutovg_font_face_t* fontface = plutovg_font_face_load_from_data(data, index);
|
||||
plutovg_font_t* font = plutovg_font_load_from_face(fontface, size);
|
||||
plutovg_font_face_destroy(fontface);
|
||||
return font;
|
||||
}
|
||||
|
||||
plutovg_font_t* plutovg_font_load_from_face(plutovg_font_face_t* face, double size)
|
||||
{
|
||||
if(face == NULL)
|
||||
return NULL;
|
||||
|
||||
plutovg_font_t* font = malloc(sizeof(plutovg_font_t));
|
||||
font->ref = 1;
|
||||
font->size = size;
|
||||
font->face = plutovg_font_face_reference(face);
|
||||
return font;
|
||||
}
|
||||
|
||||
plutovg_font_t* plutovg_font_reference(plutovg_font_t* font)
|
||||
{
|
||||
if(font == NULL)
|
||||
return NULL;
|
||||
|
||||
++font->ref;
|
||||
return font;
|
||||
}
|
||||
|
||||
void plutovg_font_destroy(plutovg_font_t* font)
|
||||
{
|
||||
if(font == NULL)
|
||||
return;
|
||||
|
||||
if(--font->ref == 0)
|
||||
{
|
||||
plutovg_font_face_destroy(font->face);
|
||||
free(font);
|
||||
}
|
||||
}
|
||||
|
||||
int plutovg_font_get_reference_count(const plutovg_font_t* font)
|
||||
{
|
||||
if(font == NULL)
|
||||
return 0;
|
||||
|
||||
return font->ref;
|
||||
}
|
||||
|
||||
plutovg_font_face_t* plutovg_font_get_face(const plutovg_font_t* font)
|
||||
{
|
||||
return font->face;
|
||||
}
|
||||
|
||||
void plutovg_font_set_face(plutovg_font_t* font, plutovg_font_face_t* face)
|
||||
{
|
||||
face = plutovg_font_face_reference(face);
|
||||
plutovg_font_face_destroy(font->face);
|
||||
font->face = face;
|
||||
}
|
||||
|
||||
void plutovg_font_set_size(plutovg_font_t* font, double size)
|
||||
{
|
||||
font->size = size;
|
||||
}
|
||||
|
||||
double plutovg_font_get_size(const plutovg_font_t* font)
|
||||
{
|
||||
return font->size;
|
||||
}
|
||||
|
||||
plutovg_font_style_t plutovg_font_get_style(const plutovg_font_t* font)
|
||||
{
|
||||
return plutovg_font_face_get_style(font->face);
|
||||
}
|
||||
|
||||
const char* plutovg_font_get_family(const plutovg_font_t* font)
|
||||
{
|
||||
return plutovg_font_face_get_family(font->face);
|
||||
}
|
||||
|
||||
double plutovg_font_get_scale(const plutovg_font_t* font)
|
||||
{
|
||||
return plutovg_font_face_get_scale(font->face, font->size);
|
||||
}
|
||||
|
||||
double plutovg_font_get_ascent(const plutovg_font_t* font)
|
||||
{
|
||||
double scale = plutovg_font_get_scale(font);
|
||||
return plutovg_font_face_get_ascent(font->face) * scale;
|
||||
}
|
||||
|
||||
double plutovg_font_get_descent(const plutovg_font_t* font)
|
||||
{
|
||||
double scale = plutovg_font_get_scale(font);
|
||||
return plutovg_font_face_get_descent(font->face) * scale;
|
||||
}
|
||||
|
||||
double plutovg_font_get_line_gap(const plutovg_font_t* font)
|
||||
{
|
||||
double scale = plutovg_font_get_scale(font);
|
||||
return plutovg_font_face_get_line_gap(font->face) * scale;
|
||||
}
|
||||
|
||||
double plutovg_font_get_leading(const plutovg_font_t* font)
|
||||
{
|
||||
double scale = plutovg_font_get_scale(font);
|
||||
return plutovg_font_face_get_leading(font->face) * scale;
|
||||
}
|
||||
|
||||
double plutovg_font_get_kerning(const plutovg_font_t* font, int ch1, int ch2)
|
||||
{
|
||||
double scale = plutovg_font_get_scale(font);
|
||||
return plutovg_font_face_get_kerning(font->face, ch1, ch2) * scale;
|
||||
}
|
||||
|
||||
static inline int decode_utf8(const char** begin, const char* end, int* codepoint)
|
||||
{
|
||||
static const int trailing[256] = {
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
|
||||
1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
|
||||
2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 3, 3, 3, 3, 3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5
|
||||
};
|
||||
|
||||
static const uint32_t offsets[6] = {
|
||||
0x00000000, 0x00003080, 0x000E2080, 0x03C82080, 0xFA082080, 0x82082080
|
||||
};
|
||||
|
||||
const char* ptr = *begin;
|
||||
int trailing_bytes = trailing[(uint8_t)(*ptr)];
|
||||
if(ptr + trailing_bytes >= end)
|
||||
return 0;
|
||||
|
||||
uint32_t output = 0;
|
||||
switch(trailing_bytes) {
|
||||
case 5: output += (uint8_t)(*ptr++); output <<= 6;
|
||||
case 4: output += (uint8_t)(*ptr++); output <<= 6;
|
||||
case 3: output += (uint8_t)(*ptr++); output <<= 6;
|
||||
case 2: output += (uint8_t)(*ptr++); output <<= 6;
|
||||
case 1: output += (uint8_t)(*ptr++); output <<= 6;
|
||||
case 0: output += (uint8_t)(*ptr++);
|
||||
}
|
||||
|
||||
output -= offsets[trailing_bytes];
|
||||
*begin = ptr;
|
||||
*codepoint = output;
|
||||
return 1;
|
||||
}
|
||||
|
||||
double plutovg_font_get_char_advance(const plutovg_font_t* font, int ch)
|
||||
{
|
||||
double scale = plutovg_font_get_scale(font);
|
||||
return plutovg_font_face_get_char_advance(font->face, ch) * scale;
|
||||
}
|
||||
|
||||
double plutovg_font_get_text_advance(const plutovg_font_t* font, const char* utf8)
|
||||
{
|
||||
return plutovg_font_get_textn_advance(font, utf8, (int)strlen(utf8));
|
||||
}
|
||||
|
||||
double plutovg_font_get_textn_advance(const plutovg_font_t* font, const char* utf8, int size)
|
||||
{
|
||||
double advance = 0;
|
||||
const char* end = utf8 + size;
|
||||
while(utf8 < end)
|
||||
{
|
||||
int ch = 0;
|
||||
if(!decode_utf8(&utf8, end, &ch))
|
||||
break;
|
||||
|
||||
advance += plutovg_font_get_char_advance(font, ch);
|
||||
}
|
||||
|
||||
return advance;
|
||||
}
|
||||
|
||||
void plutovg_font_get_char_extents(const plutovg_font_t* font, int ch, plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_matrix_t matrix;
|
||||
plutovg_font_face_get_matrix(font->face, font->size, &matrix);
|
||||
plutovg_font_face_get_char_extents(font->face, ch, rect);
|
||||
plutovg_matrix_map_rect(&matrix, rect, rect);
|
||||
}
|
||||
|
||||
void plutovg_font_get_text_extents(const plutovg_font_t* font, const char* utf8, plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_font_get_textn_extents(font, utf8, (int)strlen(utf8), rect);
|
||||
}
|
||||
|
||||
void plutovg_font_get_textn_extents(const plutovg_font_t* font, const char* utf8, int size, plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_rect_init_invalid(rect);
|
||||
double advance = 0;
|
||||
double scale = plutovg_font_get_scale(font);
|
||||
const char* end = utf8 + size;
|
||||
while(utf8 < end)
|
||||
{
|
||||
int ch = 0;
|
||||
if(!decode_utf8(&utf8, end, &ch))
|
||||
break;
|
||||
|
||||
plutovg_matrix_t matrix;
|
||||
plutovg_matrix_init_translate(&matrix, advance, 0);
|
||||
plutovg_matrix_scale(&matrix, scale, -scale);
|
||||
|
||||
plutovg_rect_t box;
|
||||
plutovg_font_face_get_char_extents(font->face, ch, &box);
|
||||
plutovg_matrix_map_rect(&matrix, &box, &box);
|
||||
plutovg_rect_unite(rect, &box);
|
||||
advance += plutovg_font_get_char_advance(font, ch);
|
||||
}
|
||||
}
|
||||
|
||||
void plutovg_font_get_extents(const plutovg_font_t* font, plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_matrix_t matrix;
|
||||
plutovg_font_face_get_matrix(font->face, font->size, &matrix);
|
||||
plutovg_font_face_get_extents(font->face, rect);
|
||||
plutovg_matrix_map_rect(&matrix, rect, rect);
|
||||
}
|
||||
|
||||
plutovg_path_t* plutovg_font_get_char_path(const plutovg_font_t* font, int ch)
|
||||
{
|
||||
plutovg_matrix_t matrix;
|
||||
plutovg_font_face_get_matrix(font->face, font->size, &matrix);
|
||||
plutovg_path_t* result = plutovg_path_create();
|
||||
plutovg_path_t* path = plutovg_font_face_get_char_path(font->face, ch);
|
||||
plutovg_path_add_path(result, path, &matrix);
|
||||
plutovg_path_destroy(path);
|
||||
return result;
|
||||
}
|
||||
|
||||
plutovg_path_t* plutovg_font_get_text_path(const plutovg_font_t* font, const char* utf8)
|
||||
{
|
||||
return plutovg_font_get_textn_path(font, utf8, (int)strlen(utf8));
|
||||
}
|
||||
|
||||
plutovg_path_t* plutovg_font_get_textn_path(const plutovg_font_t* font, const char* utf8, int size)
|
||||
{
|
||||
plutovg_path_t* result = plutovg_path_create();
|
||||
double advance = 0;
|
||||
double scale = plutovg_font_get_scale(font);
|
||||
const char* end = utf8 + size;
|
||||
while(utf8 < end)
|
||||
{
|
||||
int ch = 0;
|
||||
if(!decode_utf8(&utf8, end, &ch))
|
||||
break;
|
||||
|
||||
plutovg_matrix_t matrix;
|
||||
plutovg_matrix_init_translate(&matrix, advance, 0);
|
||||
plutovg_matrix_scale(&matrix, scale, -scale);
|
||||
|
||||
plutovg_path_t* path = plutovg_font_face_get_char_path(font->face, ch);
|
||||
plutovg_path_add_path(result, path, &matrix);
|
||||
plutovg_path_destroy(path);
|
||||
advance += plutovg_font_get_char_advance(font, ch);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
@@ -0,0 +1,748 @@
|
||||
#include "plutovg-private.h"
|
||||
|
||||
#include <math.h>
|
||||
|
||||
void plutovg_rect_init(plutovg_rect_t* rect, double x, double y, double w, double h)
|
||||
{
|
||||
rect->x = x;
|
||||
rect->y = y;
|
||||
rect->w = w;
|
||||
rect->h = h;
|
||||
}
|
||||
|
||||
void plutovg_rect_init_empty(plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_rect_init(rect, 0, 0, 0, 0);
|
||||
}
|
||||
|
||||
void plutovg_rect_init_invalid(plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_rect_init(rect, 0, 0, -1, -1);
|
||||
}
|
||||
|
||||
int plutovg_rect_empty(const plutovg_rect_t* rect)
|
||||
{
|
||||
return rect->w <= 0.0 || rect->h <= 0.0;
|
||||
}
|
||||
|
||||
int plutovg_rect_invalid(const plutovg_rect_t* rect)
|
||||
{
|
||||
return rect->w < 0.0 || rect->h < 0.0;
|
||||
}
|
||||
|
||||
void plutovg_rect_unite(plutovg_rect_t* rect, const plutovg_rect_t* source)
|
||||
{
|
||||
if(plutovg_rect_invalid(source))
|
||||
return;
|
||||
|
||||
if(plutovg_rect_invalid(rect))
|
||||
{
|
||||
plutovg_rect_init(rect, source->x, source->y, source->w, source->h);
|
||||
return;
|
||||
}
|
||||
|
||||
double l = MIN(rect->x, source->x);
|
||||
double t = MIN(rect->y, source->y);
|
||||
double r = MAX(rect->x + rect->w, source->x + source->w);
|
||||
double b = MAX(rect->y + rect->h, source->y + source->h);
|
||||
|
||||
plutovg_rect_init(rect, l, t, r - l, b - t);
|
||||
}
|
||||
|
||||
void plutovg_rect_intersect(plutovg_rect_t* rect, const plutovg_rect_t* source)
|
||||
{
|
||||
if(plutovg_rect_invalid(source))
|
||||
return;
|
||||
|
||||
if(plutovg_rect_invalid(rect))
|
||||
{
|
||||
plutovg_rect_init(rect, source->x, source->y, source->w, source->h);
|
||||
return;
|
||||
}
|
||||
|
||||
double l = MAX(rect->x, source->x);
|
||||
double t = MAX(rect->y, source->y);
|
||||
double r = MIN(rect->x + rect->w, source->x + source->w);
|
||||
double b = MIN(rect->y + rect->h, source->y + source->h);
|
||||
|
||||
plutovg_rect_init(rect, l, t, r - l, b - t);
|
||||
}
|
||||
|
||||
void plutovg_matrix_init(plutovg_matrix_t* matrix, double m00, double m10, double m01, double m11, double m02, double m12)
|
||||
{
|
||||
matrix->m00 = m00; matrix->m10 = m10;
|
||||
matrix->m01 = m01; matrix->m11 = m11;
|
||||
matrix->m02 = m02; matrix->m12 = m12;
|
||||
}
|
||||
|
||||
void plutovg_matrix_init_identity(plutovg_matrix_t* matrix)
|
||||
{
|
||||
matrix->m00 = 1.0; matrix->m10 = 0.0;
|
||||
matrix->m01 = 0.0; matrix->m11 = 1.0;
|
||||
matrix->m02 = 0.0; matrix->m12 = 0.0;
|
||||
}
|
||||
|
||||
void plutovg_matrix_init_translate(plutovg_matrix_t* matrix, double x, double y)
|
||||
{
|
||||
plutovg_matrix_init(matrix, 1.0, 0.0, 0.0, 1.0, x, y);
|
||||
}
|
||||
|
||||
void plutovg_matrix_init_scale(plutovg_matrix_t* matrix, double x, double y)
|
||||
{
|
||||
plutovg_matrix_init(matrix, x, 0.0, 0.0, y, 0.0, 0.0);
|
||||
}
|
||||
|
||||
void plutovg_matrix_init_shear(plutovg_matrix_t* matrix, double x, double y)
|
||||
{
|
||||
plutovg_matrix_init(matrix, 1.0, tan(y), tan(x), 1.0, 0.0, 0.0);
|
||||
}
|
||||
|
||||
void plutovg_matrix_init_rotate(plutovg_matrix_t* matrix, double radians)
|
||||
{
|
||||
double c = cos(radians);
|
||||
double s = sin(radians);
|
||||
|
||||
plutovg_matrix_init(matrix, c, s, -s, c, 0.0, 0.0);
|
||||
}
|
||||
|
||||
void plutovg_matrix_init_rotate_translate(plutovg_matrix_t* matrix, double radians, double x, double y)
|
||||
{
|
||||
double c = cos(radians);
|
||||
double s = sin(radians);
|
||||
|
||||
double cx = x * (1 - c) + y * s;
|
||||
double cy = y * (1 - c) - x * s;
|
||||
|
||||
plutovg_matrix_init(matrix, c, s, -s, c, cx, cy);
|
||||
}
|
||||
|
||||
void plutovg_matrix_translate(plutovg_matrix_t* matrix, double x, double y)
|
||||
{
|
||||
plutovg_matrix_t m;
|
||||
plutovg_matrix_init_translate(&m, x, y);
|
||||
plutovg_matrix_multiply(matrix, &m, matrix);
|
||||
}
|
||||
|
||||
void plutovg_matrix_scale(plutovg_matrix_t* matrix, double x, double y)
|
||||
{
|
||||
plutovg_matrix_t m;
|
||||
plutovg_matrix_init_scale(&m, x, y);
|
||||
plutovg_matrix_multiply(matrix, &m, matrix);
|
||||
}
|
||||
|
||||
void plutovg_matrix_shear(plutovg_matrix_t* matrix, double x, double y)
|
||||
{
|
||||
plutovg_matrix_t m;
|
||||
plutovg_matrix_init_shear(&m, x, y);
|
||||
plutovg_matrix_multiply(matrix, &m, matrix);
|
||||
}
|
||||
|
||||
void plutovg_matrix_rotate(plutovg_matrix_t* matrix, double radians)
|
||||
{
|
||||
plutovg_matrix_t m;
|
||||
plutovg_matrix_init_rotate(&m, radians);
|
||||
plutovg_matrix_multiply(matrix, &m, matrix);
|
||||
}
|
||||
|
||||
void plutovg_matrix_rotate_translate(plutovg_matrix_t* matrix, double radians, double x, double y)
|
||||
{
|
||||
plutovg_matrix_t m;
|
||||
plutovg_matrix_init_rotate_translate(&m, radians, x, y);
|
||||
plutovg_matrix_multiply(matrix, &m, matrix);
|
||||
}
|
||||
|
||||
void plutovg_matrix_multiply(plutovg_matrix_t* matrix, const plutovg_matrix_t* a, const plutovg_matrix_t* b)
|
||||
{
|
||||
double m00 = a->m00 * b->m00 + a->m10 * b->m01;
|
||||
double m10 = a->m00 * b->m10 + a->m10 * b->m11;
|
||||
double m01 = a->m01 * b->m00 + a->m11 * b->m01;
|
||||
double m11 = a->m01 * b->m10 + a->m11 * b->m11;
|
||||
double m02 = a->m02 * b->m00 + a->m12 * b->m01 + b->m02;
|
||||
double m12 = a->m02 * b->m10 + a->m12 * b->m11 + b->m12;
|
||||
|
||||
plutovg_matrix_init(matrix, m00, m10, m01, m11, m02, m12);
|
||||
}
|
||||
|
||||
int plutovg_matrix_invert(plutovg_matrix_t* matrix)
|
||||
{
|
||||
double det = (matrix->m00 * matrix->m11 - matrix->m10 * matrix->m01);
|
||||
if(det == 0.0)
|
||||
return 0;
|
||||
|
||||
double inv_det = 1.0 / det;
|
||||
double m00 = matrix->m00 * inv_det;
|
||||
double m10 = matrix->m10 * inv_det;
|
||||
double m01 = matrix->m01 * inv_det;
|
||||
double m11 = matrix->m11 * inv_det;
|
||||
double m02 = (matrix->m01 * matrix->m12 - matrix->m11 * matrix->m02) * inv_det;
|
||||
double m12 = (matrix->m10 * matrix->m02 - matrix->m00 * matrix->m12) * inv_det;
|
||||
|
||||
plutovg_matrix_init(matrix, m11, -m10, -m01, m00, m02, m12);
|
||||
return 1;
|
||||
}
|
||||
|
||||
void plutovg_matrix_map(const plutovg_matrix_t* matrix, double x, double y, double* _x, double* _y)
|
||||
{
|
||||
*_x = x * matrix->m00 + y * matrix->m01 + matrix->m02;
|
||||
*_y = x * matrix->m10 + y * matrix->m11 + matrix->m12;
|
||||
}
|
||||
|
||||
void plutovg_matrix_map_point(const plutovg_matrix_t* matrix, const plutovg_point_t* src, plutovg_point_t* dst)
|
||||
{
|
||||
plutovg_matrix_map(matrix, src->x, src->y, &dst->x, &dst->y);
|
||||
}
|
||||
|
||||
void plutovg_matrix_map_rect(const plutovg_matrix_t* matrix, const plutovg_rect_t* src, plutovg_rect_t* dst)
|
||||
{
|
||||
plutovg_point_t p[4];
|
||||
p[0].x = src->x;
|
||||
p[0].y = src->y;
|
||||
p[1].x = src->x + src->w;
|
||||
p[1].y = src->y;
|
||||
p[2].x = src->x + src->w;
|
||||
p[2].y = src->y + src->h;
|
||||
p[3].x = src->x;
|
||||
p[3].y = src->y + src->h;
|
||||
|
||||
plutovg_matrix_map_point(matrix, &p[0], &p[0]);
|
||||
plutovg_matrix_map_point(matrix, &p[1], &p[1]);
|
||||
plutovg_matrix_map_point(matrix, &p[2], &p[2]);
|
||||
plutovg_matrix_map_point(matrix, &p[3], &p[3]);
|
||||
|
||||
double l = p[0].x;
|
||||
double t = p[0].y;
|
||||
double r = p[0].x;
|
||||
double b = p[0].y;
|
||||
|
||||
for(int i = 1;i < 4;i++)
|
||||
{
|
||||
if(p[i].x < l) l = p[i].x;
|
||||
if(p[i].x > r) r = p[i].x;
|
||||
if(p[i].y < t) t = p[i].y;
|
||||
if(p[i].y > b) b = p[i].y;
|
||||
}
|
||||
|
||||
dst->x = l;
|
||||
dst->y = t;
|
||||
dst->w = r - l;
|
||||
dst->h = b - t;
|
||||
}
|
||||
|
||||
plutovg_path_t* plutovg_path_create(void)
|
||||
{
|
||||
plutovg_path_t* path = malloc(sizeof(plutovg_path_t));
|
||||
path->ref = 1;
|
||||
path->contours = 0;
|
||||
path->start.x = 0.0;
|
||||
path->start.y = 0.0;
|
||||
plutovg_array_init(path->elements);
|
||||
plutovg_array_init(path->points);
|
||||
return path;
|
||||
}
|
||||
|
||||
plutovg_path_t* plutovg_path_reference(plutovg_path_t* path)
|
||||
{
|
||||
if(path == NULL)
|
||||
return NULL;
|
||||
|
||||
++path->ref;
|
||||
return path;
|
||||
}
|
||||
|
||||
void plutovg_path_destroy(plutovg_path_t* path)
|
||||
{
|
||||
if(path == NULL)
|
||||
return;
|
||||
|
||||
if(--path->ref == 0)
|
||||
{
|
||||
free(path->elements.data);
|
||||
free(path->points.data);
|
||||
free(path);
|
||||
}
|
||||
}
|
||||
|
||||
int plutovg_path_get_reference_count(const plutovg_path_t* path)
|
||||
{
|
||||
if(path == NULL)
|
||||
return 0;
|
||||
|
||||
return path->ref;
|
||||
}
|
||||
|
||||
void plutovg_path_move_to(plutovg_path_t* path, double x, double y)
|
||||
{
|
||||
plutovg_array_ensure(path->elements, 1);
|
||||
plutovg_array_ensure(path->points, 1);
|
||||
|
||||
path->elements.data[path->elements.size] = plutovg_path_element_move_to;
|
||||
path->elements.size += 1;
|
||||
path->contours += 1;
|
||||
|
||||
path->points.data[path->points.size].x = x;
|
||||
path->points.data[path->points.size].y = y;
|
||||
path->points.size += 1;
|
||||
|
||||
path->start.x = x;
|
||||
path->start.y = y;
|
||||
}
|
||||
|
||||
void plutovg_path_line_to(plutovg_path_t* path, double x, double y)
|
||||
{
|
||||
plutovg_array_ensure(path->elements, 1);
|
||||
plutovg_array_ensure(path->points, 1);
|
||||
|
||||
path->elements.data[path->elements.size] = plutovg_path_element_line_to;
|
||||
path->elements.size += 1;
|
||||
|
||||
path->points.data[path->points.size].x = x;
|
||||
path->points.data[path->points.size].y = y;
|
||||
path->points.size += 1;
|
||||
}
|
||||
|
||||
void plutovg_path_quad_to(plutovg_path_t* path, double x1, double y1, double x2, double y2)
|
||||
{
|
||||
double x, y;
|
||||
plutovg_path_get_current_point(path, &x, &y);
|
||||
|
||||
double cx = 2.0 / 3.0 * x1 + 1.0 / 3.0 * x;
|
||||
double cy = 2.0 / 3.0 * y1 + 1.0 / 3.0 * y;
|
||||
double cx1 = 2.0 / 3.0 * x1 + 1.0 / 3.0 * x2;
|
||||
double cy1 = 2.0 / 3.0 * y1 + 1.0 / 3.0 * y2;
|
||||
plutovg_path_cubic_to(path, cx, cy, cx1, cy1, x2, y2);
|
||||
}
|
||||
|
||||
void plutovg_path_cubic_to(plutovg_path_t* path, double x1, double y1, double x2, double y2, double x3, double y3)
|
||||
{
|
||||
plutovg_array_ensure(path->elements, 1);
|
||||
plutovg_array_ensure(path->points, 3);
|
||||
|
||||
path->elements.data[path->elements.size] = plutovg_path_element_cubic_to;
|
||||
path->elements.size += 1;
|
||||
|
||||
path->points.data[path->points.size].x = x1;
|
||||
path->points.data[path->points.size].y = y1;
|
||||
path->points.size += 1;
|
||||
|
||||
path->points.data[path->points.size].x = x2;
|
||||
path->points.data[path->points.size].y = y2;
|
||||
path->points.size += 1;
|
||||
|
||||
path->points.data[path->points.size].x = x3;
|
||||
path->points.data[path->points.size].y = y3;
|
||||
path->points.size += 1;
|
||||
}
|
||||
|
||||
void plutovg_path_arc_to(plutovg_path_t* path, double x1, double y1, double x2, double y2, double radius)
|
||||
{
|
||||
double x0, y0;
|
||||
plutovg_path_get_current_point(path, &x0, &y0);
|
||||
if((x0 == x1 && y0 == y1) || (x1 == x2 && y1 == y2) || radius == 0.0)
|
||||
{
|
||||
plutovg_path_line_to(path, x1, y2);
|
||||
return;
|
||||
}
|
||||
|
||||
double dir = (x2 - x1) * (y0 - y1) + (y2 - y1) * (x1 - x0);
|
||||
if(dir == 0.0)
|
||||
{
|
||||
plutovg_path_line_to(path, x1, y2);
|
||||
return;
|
||||
}
|
||||
|
||||
double a2 = (x0 - x1) * (x0 - x1) + (y0 - y1) * (y0 - y1);
|
||||
double b2 = (x1 - x2) * (x1 - x2) + (y1 - y2) * (y1 - y2);
|
||||
double c2 = (x0 - x2) * (x0 - x2) + (y0 - y2) * (y0 - y2);
|
||||
|
||||
double cosx = (a2 + b2 - c2) / (2 * sqrt(a2 * b2));
|
||||
double sinx = sqrt(1 - cosx * cosx);
|
||||
double d = radius / ((1 - cosx) / sinx);
|
||||
|
||||
double anx = (x1 - x0) / sqrt(a2);
|
||||
double any = (y1 - y0) / sqrt(a2);
|
||||
double bnx = (x1 - x2) / sqrt(b2);
|
||||
double bny = (y1 - y2) / sqrt(b2);
|
||||
|
||||
double x3 = x1 - anx * d;
|
||||
double y3 = y1 - any * d;
|
||||
double x4 = x1 - bnx * d;
|
||||
double y4 = y1 - bny * d;
|
||||
|
||||
int ccw = dir < 0.0;
|
||||
double cx = x3 + any * radius * (ccw ? 1 : -1);
|
||||
double cy = y3 - anx * radius * (ccw ? 1 : -1);
|
||||
double a0 = atan2(y3 - cy, x3 - cx);
|
||||
double a1 = atan2(y4 - cy, x4 - cx);
|
||||
|
||||
plutovg_path_line_to(path, x3, y3);
|
||||
plutovg_path_add_arc(path, cx, cy, radius, a0, a1, ccw);
|
||||
}
|
||||
|
||||
void plutovg_path_close(plutovg_path_t* path)
|
||||
{
|
||||
if(path->elements.size == 0)
|
||||
return;
|
||||
|
||||
if(path->elements.data[path->elements.size - 1] == plutovg_path_element_close)
|
||||
return;
|
||||
|
||||
plutovg_array_ensure(path->elements, 1);
|
||||
plutovg_array_ensure(path->points, 1);
|
||||
|
||||
path->elements.data[path->elements.size] = plutovg_path_element_close;
|
||||
path->elements.size += 1;
|
||||
|
||||
path->points.data[path->points.size].x = path->start.x;
|
||||
path->points.data[path->points.size].y = path->start.y;
|
||||
path->points.size += 1;
|
||||
}
|
||||
|
||||
static inline void rel_to_abs(const plutovg_path_t* path, double* x, double* y)
|
||||
{
|
||||
double _x, _y;
|
||||
plutovg_path_get_current_point(path, &_x, &_y);
|
||||
|
||||
*x += _x;
|
||||
*y += _y;
|
||||
}
|
||||
|
||||
void plutovg_path_rel_move_to(plutovg_path_t* path, double dx, double dy)
|
||||
{
|
||||
rel_to_abs(path, &dx, &dy);
|
||||
plutovg_path_move_to(path, dx, dy);
|
||||
}
|
||||
|
||||
void plutovg_path_rel_line_to(plutovg_path_t* path, double dx, double dy)
|
||||
{
|
||||
rel_to_abs(path, &dx, &dy);
|
||||
plutovg_path_line_to(path, dx, dy);
|
||||
}
|
||||
|
||||
void plutovg_path_rel_quad_to(plutovg_path_t* path, double dx1, double dy1, double dx2, double dy2)
|
||||
{
|
||||
rel_to_abs(path, &dx1, &dy1);
|
||||
rel_to_abs(path, &dx2, &dy2);
|
||||
plutovg_path_quad_to(path, dx1, dy1, dx2, dy2);
|
||||
}
|
||||
|
||||
void plutovg_path_rel_cubic_to(plutovg_path_t* path, double dx1, double dy1, double dx2, double dy2, double dx3, double dy3)
|
||||
{
|
||||
rel_to_abs(path, &dx1, &dy1);
|
||||
rel_to_abs(path, &dx2, &dy2);
|
||||
rel_to_abs(path, &dx3, &dy3);
|
||||
plutovg_path_cubic_to(path, dx1, dy1, dx2, dy2, dx3, dy3);
|
||||
}
|
||||
|
||||
void plutovg_path_rel_arc_to(plutovg_path_t* path, double dx1, double dy1, double dx2, double dy2, double radius)
|
||||
{
|
||||
rel_to_abs(path, &dx1, &dy1);
|
||||
rel_to_abs(path, &dx2, &dy2);
|
||||
plutovg_path_arc_to(path, dx1, dy1, dx2, dy2, radius);
|
||||
}
|
||||
|
||||
void plutovg_path_add_rect(plutovg_path_t* path, double x, double y, double w, double h)
|
||||
{
|
||||
plutovg_path_move_to(path, x, y);
|
||||
plutovg_path_line_to(path, x + w, y);
|
||||
plutovg_path_line_to(path, x + w, y + h);
|
||||
plutovg_path_line_to(path, x, y + h);
|
||||
plutovg_path_line_to(path, x, y);
|
||||
plutovg_path_close(path);
|
||||
}
|
||||
|
||||
void plutovg_path_add_round_rect(plutovg_path_t* path, double x, double y, double w, double h, double rx, double ry)
|
||||
{
|
||||
rx = MIN(rx, w * 0.5);
|
||||
ry = MIN(ry, h * 0.5);
|
||||
|
||||
double right = x + w;
|
||||
double bottom = y + h;
|
||||
|
||||
double cpx = rx * KAPPA;
|
||||
double cpy = ry * KAPPA;
|
||||
|
||||
plutovg_path_move_to(path, x, y+ry);
|
||||
plutovg_path_cubic_to(path, x, y+ry-cpy, x+rx-cpx, y, x+rx, y);
|
||||
plutovg_path_line_to(path, right-rx, y);
|
||||
plutovg_path_cubic_to(path, right-rx+cpx, y, right, y+ry-cpy, right, y+ry);
|
||||
plutovg_path_line_to(path, right, bottom-ry);
|
||||
plutovg_path_cubic_to(path, right, bottom-ry+cpy, right-rx+cpx, bottom, right-rx, bottom);
|
||||
plutovg_path_line_to(path, x+rx, bottom);
|
||||
plutovg_path_cubic_to(path, x+rx-cpx, bottom, x, bottom-ry+cpy, x, bottom-ry);
|
||||
plutovg_path_line_to(path, x, y+ry);
|
||||
plutovg_path_close(path);
|
||||
}
|
||||
|
||||
void plutovg_path_add_ellipse(plutovg_path_t* path, double cx, double cy, double rx, double ry)
|
||||
{
|
||||
double left = cx - rx;
|
||||
double top = cy - ry;
|
||||
double right = cx + rx;
|
||||
double bottom = cy + ry;
|
||||
|
||||
double cpx = rx * KAPPA;
|
||||
double cpy = ry * KAPPA;
|
||||
|
||||
plutovg_path_move_to(path, cx, top);
|
||||
plutovg_path_cubic_to(path, cx+cpx, top, right, cy-cpy, right, cy);
|
||||
plutovg_path_cubic_to(path, right, cy+cpy, cx+cpx, bottom, cx, bottom);
|
||||
plutovg_path_cubic_to(path, cx-cpx, bottom, left, cy+cpy, left, cy);
|
||||
plutovg_path_cubic_to(path, left, cy-cpy, cx-cpx, top, cx, top);
|
||||
plutovg_path_close(path);
|
||||
}
|
||||
|
||||
void plutovg_path_add_circle(plutovg_path_t* path, double cx, double cy, double r)
|
||||
{
|
||||
plutovg_path_add_ellipse(path, cx, cy, r, r);
|
||||
}
|
||||
|
||||
void plutovg_path_add_arc(plutovg_path_t* path, double cx, double cy, double r, double a0, double a1, int ccw)
|
||||
{
|
||||
double da = a1 - a0;
|
||||
if(fabs(da) > TWO_PI) {
|
||||
da = TWO_PI;
|
||||
} else if(da != 0.0 && ccw != (da < 0.0)) {
|
||||
da += TWO_PI * (ccw ? -1 : 1);
|
||||
}
|
||||
|
||||
int seg_n = (int)(ceil(fabs(da) / HALF_PI));
|
||||
double seg_a = da / seg_n;
|
||||
double d = (seg_a / HALF_PI) * KAPPA * r;
|
||||
|
||||
double a = a0;
|
||||
|
||||
double ax = cx + cos(a) * r;
|
||||
double ay = cy + sin(a) * r;
|
||||
|
||||
double dx = -sin(a) * d;
|
||||
double dy = cos(a) * d;
|
||||
|
||||
|
||||
if(path->points.size == 0)
|
||||
plutovg_path_move_to(path, ax, ay);
|
||||
else
|
||||
plutovg_path_line_to(path, ax, ay);
|
||||
|
||||
for(int i = 0; i < seg_n; i++) {
|
||||
double cp1x = ax + dx;
|
||||
double cp1y = ay + dy;
|
||||
|
||||
a += seg_a;
|
||||
|
||||
ax = cx + cos(a) * r;
|
||||
ay = cy + sin(a) * r;
|
||||
|
||||
dx = -sin(a) * d;
|
||||
dy = cos(a) * d;
|
||||
|
||||
double cp2x = ax - dx;
|
||||
double cp2y = ay - dy;
|
||||
|
||||
plutovg_path_cubic_to(path, cp1x, cp1y, cp2x, cp2y, ax, ay);
|
||||
}
|
||||
}
|
||||
|
||||
void plutovg_path_add_path(plutovg_path_t* path, const plutovg_path_t* source, const plutovg_matrix_t* matrix)
|
||||
{
|
||||
plutovg_array_ensure(path->elements, source->elements.size);
|
||||
plutovg_array_ensure(path->points, source->points.size);
|
||||
|
||||
plutovg_point_t* points = path->points.data + path->points.size;
|
||||
const plutovg_point_t* data = source->points.data;
|
||||
const plutovg_point_t* end = data + source->points.size;
|
||||
while(data < end)
|
||||
{
|
||||
if(matrix)
|
||||
plutovg_matrix_map_point(matrix, data, points);
|
||||
else
|
||||
memcpy(points, data, sizeof(plutovg_point_t));
|
||||
|
||||
points += 1;
|
||||
data += 1;
|
||||
}
|
||||
|
||||
plutovg_path_element_t* elements = path->elements.data + path->elements.size;
|
||||
memcpy(elements, source->elements.data, (size_t)source->elements.size * sizeof(plutovg_path_element_t));
|
||||
|
||||
path->elements.size += source->elements.size;
|
||||
path->points.size += source->points.size;
|
||||
path->contours += source->contours;
|
||||
path->start = source->start;
|
||||
}
|
||||
|
||||
void plutovg_path_transform(plutovg_path_t* path, const plutovg_matrix_t* matrix)
|
||||
{
|
||||
plutovg_point_t* points = path->points.data;
|
||||
plutovg_point_t* end = points + path->points.size;
|
||||
while(points < end)
|
||||
{
|
||||
plutovg_matrix_map_point(matrix, points, points);
|
||||
points += 1;
|
||||
}
|
||||
}
|
||||
|
||||
void plutovg_path_get_current_point(const plutovg_path_t* path, double* x, double* y)
|
||||
{
|
||||
if(x) *x = 0.0;
|
||||
if(y) *y = 0.0;
|
||||
|
||||
if(path->points.size == 0)
|
||||
return;
|
||||
|
||||
if(x) *x = path->points.data[path->points.size - 1].x;
|
||||
if(y) *y = path->points.data[path->points.size - 1].y;
|
||||
}
|
||||
|
||||
int plutovg_path_get_element_count(const plutovg_path_t* path)
|
||||
{
|
||||
return path->elements.size;
|
||||
}
|
||||
|
||||
plutovg_path_element_t* plutovg_path_get_elements(const plutovg_path_t* path)
|
||||
{
|
||||
return path->elements.data;
|
||||
}
|
||||
|
||||
int plutovg_path_get_point_count(const plutovg_path_t* path)
|
||||
{
|
||||
return path->points.size;
|
||||
}
|
||||
|
||||
plutovg_point_t* plutovg_path_get_points(const plutovg_path_t* path)
|
||||
{
|
||||
return path->points.data;
|
||||
}
|
||||
|
||||
void plutovg_path_clear(plutovg_path_t* path)
|
||||
{
|
||||
path->elements.size = 0;
|
||||
path->points.size = 0;
|
||||
path->contours = 0;
|
||||
path->start.x = 0.0;
|
||||
path->start.y = 0.0;
|
||||
}
|
||||
|
||||
int plutovg_path_empty(const plutovg_path_t* path)
|
||||
{
|
||||
return path->elements.size == 0;
|
||||
}
|
||||
|
||||
plutovg_path_t* plutovg_path_clone(const plutovg_path_t* path)
|
||||
{
|
||||
plutovg_path_t* result = plutovg_path_create();
|
||||
plutovg_array_ensure(result->elements, path->elements.size);
|
||||
plutovg_array_ensure(result->points, path->points.size);
|
||||
|
||||
memcpy(result->elements.data, path->elements.data, (size_t)path->elements.size * sizeof(plutovg_path_element_t));
|
||||
memcpy(result->points.data, path->points.data, (size_t)path->points.size * sizeof(plutovg_point_t));
|
||||
|
||||
result->elements.size = path->elements.size;
|
||||
result->points.size = path->points.size;
|
||||
result->contours = path->contours;
|
||||
result->start = path->start;
|
||||
return result;
|
||||
}
|
||||
|
||||
typedef struct {
|
||||
double x1; double y1;
|
||||
double x2; double y2;
|
||||
double x3; double y3;
|
||||
double x4; double y4;
|
||||
} bezier_t;
|
||||
|
||||
static inline void split(const bezier_t* b, bezier_t* first, bezier_t* second)
|
||||
{
|
||||
double c = (b->x2 + b->x3) * 0.5;
|
||||
first->x2 = (b->x1 + b->x2) * 0.5;
|
||||
second->x3 = (b->x3 + b->x4) * 0.5;
|
||||
first->x1 = b->x1;
|
||||
second->x4 = b->x4;
|
||||
first->x3 = (first->x2 + c) * 0.5;
|
||||
second->x2 = (second->x3 + c) * 0.5;
|
||||
first->x4 = second->x1 = (first->x3 + second->x2) * 0.5;
|
||||
|
||||
c = (b->y2 + b->y3) * 0.5;
|
||||
first->y2 = (b->y1 + b->y2) * 0.5;
|
||||
second->y3 = (b->y3 + b->y4) * 0.5;
|
||||
first->y1 = b->y1;
|
||||
second->y4 = b->y4;
|
||||
first->y3 = (first->y2 + c) * 0.5;
|
||||
second->y2 = (second->y3 + c) * 0.5;
|
||||
first->y4 = second->y1 = (first->y3 + second->y2) * 0.5;
|
||||
}
|
||||
|
||||
static void flatten(plutovg_path_t* path, const plutovg_point_t* p0, const plutovg_point_t* p1, const plutovg_point_t* p2, const plutovg_point_t* p3)
|
||||
{
|
||||
bezier_t beziers[32];
|
||||
beziers[0].x1 = p0->x;
|
||||
beziers[0].y1 = p0->y;
|
||||
beziers[0].x2 = p1->x;
|
||||
beziers[0].y2 = p1->y;
|
||||
beziers[0].x3 = p2->x;
|
||||
beziers[0].y3 = p2->y;
|
||||
beziers[0].x4 = p3->x;
|
||||
beziers[0].y4 = p3->y;
|
||||
|
||||
const double threshold = 0.25;
|
||||
|
||||
bezier_t* b = beziers;
|
||||
while(b >= beziers)
|
||||
{
|
||||
double y4y1 = b->y4 - b->y1;
|
||||
double x4x1 = b->x4 - b->x1;
|
||||
double l = fabs(x4x1) + fabs(y4y1);
|
||||
double d;
|
||||
if(l > 1.0)
|
||||
{
|
||||
d = fabs((x4x1)*(b->y1 - b->y2) - (y4y1)*(b->x1 - b->x2)) + fabs((x4x1)*(b->y1 - b->y3) - (y4y1)*(b->x1 - b->x3));
|
||||
}
|
||||
else
|
||||
{
|
||||
d = fabs(b->x1 - b->x2) + fabs(b->y1 - b->y2) + fabs(b->x1 - b->x3) + fabs(b->y1 - b->y3);
|
||||
l = 1.0;
|
||||
}
|
||||
|
||||
if(d < threshold*l || b == beziers + 31)
|
||||
{
|
||||
plutovg_path_line_to(path, b->x4, b->y4);
|
||||
--b;
|
||||
}
|
||||
else
|
||||
{
|
||||
split(b, b+1, b);
|
||||
++b;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
plutovg_path_t* plutovg_path_clone_flat(const plutovg_path_t* path)
|
||||
{
|
||||
plutovg_path_t* result = plutovg_path_create();
|
||||
plutovg_array_ensure(result->elements, path->elements.size);
|
||||
plutovg_array_ensure(result->points, path->points.size);
|
||||
plutovg_point_t* points = path->points.data;
|
||||
for(int i = 0;i < path->elements.size;i++)
|
||||
{
|
||||
switch(path->elements.data[i]) {
|
||||
case plutovg_path_element_move_to:
|
||||
plutovg_path_move_to(result, points[0].x, points[0].y);
|
||||
points += 1;
|
||||
break;
|
||||
case plutovg_path_element_line_to:
|
||||
case plutovg_path_element_close:
|
||||
plutovg_path_line_to(result, points[0].x, points[0].y);
|
||||
points += 1;
|
||||
break;
|
||||
case plutovg_path_element_cubic_to:
|
||||
{
|
||||
plutovg_point_t p0;
|
||||
plutovg_path_get_current_point(result, &p0.x, &p0.y);
|
||||
flatten(result, &p0, points, points + 1, points + 2);
|
||||
points += 3;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
@@ -0,0 +1,402 @@
|
||||
#include "plutovg-private.h"
|
||||
|
||||
void plutovg_color_init_rgb(plutovg_color_t* color, double r, double g, double b)
|
||||
{
|
||||
plutovg_color_init_rgba(color, r, g, b, 1.0);
|
||||
}
|
||||
|
||||
void plutovg_color_init_rgba(plutovg_color_t* color, double r, double g, double b, double a)
|
||||
{
|
||||
color->r = CLAMP(r, 0.0, 1.0);
|
||||
color->g = CLAMP(g, 0.0, 1.0);
|
||||
color->b = CLAMP(b, 0.0, 1.0);
|
||||
color->a = CLAMP(a, 0.0, 1.0);
|
||||
}
|
||||
|
||||
void plutovg_color_init_rgb8(plutovg_color_t* color, unsigned char r, unsigned char g, unsigned char b)
|
||||
{
|
||||
plutovg_color_init_rgba8(color, r, g, b, 255);
|
||||
}
|
||||
|
||||
void plutovg_color_init_rgba8(plutovg_color_t* color, unsigned char r, unsigned char g, unsigned char b, unsigned char a)
|
||||
{
|
||||
plutovg_color_init_rgba(color, r / 255.0, g / 255.0, b / 255.0, a / 255.0);
|
||||
}
|
||||
|
||||
plutovg_gradient_t* plutovg_gradient_create_linear(double x1, double y1, double x2, double y2)
|
||||
{
|
||||
plutovg_gradient_t* gradient = malloc(sizeof(plutovg_gradient_t));
|
||||
gradient->ref = 1;
|
||||
gradient->type = plutovg_gradient_type_linear;
|
||||
gradient->spread = plutovg_spread_method_pad;
|
||||
gradient->opacity = 1.0;
|
||||
plutovg_array_init(gradient->stops);
|
||||
plutovg_matrix_init_identity(&gradient->matrix);
|
||||
plutovg_gradient_set_values_linear(gradient, x1, y1, x2, y2);
|
||||
return gradient;
|
||||
}
|
||||
|
||||
plutovg_gradient_t* plutovg_gradient_create_radial(double cx, double cy, double cr, double fx, double fy, double fr)
|
||||
{
|
||||
plutovg_gradient_t* gradient = malloc(sizeof(plutovg_gradient_t));
|
||||
gradient->ref = 1;
|
||||
gradient->type = plutovg_gradient_type_radial;
|
||||
gradient->spread = plutovg_spread_method_pad;
|
||||
gradient->opacity = 1.0;
|
||||
plutovg_array_init(gradient->stops);
|
||||
plutovg_matrix_init_identity(&gradient->matrix);
|
||||
plutovg_gradient_set_values_radial(gradient, cx, cy, cr, fx, fy, fr);
|
||||
return gradient;
|
||||
}
|
||||
|
||||
plutovg_gradient_t* plutovg_gradient_reference(plutovg_gradient_t* gradient)
|
||||
{
|
||||
if(gradient == NULL)
|
||||
return NULL;
|
||||
|
||||
++gradient->ref;
|
||||
return gradient;
|
||||
}
|
||||
|
||||
void plutovg_gradient_destroy(plutovg_gradient_t* gradient)
|
||||
{
|
||||
if(gradient == NULL)
|
||||
return;
|
||||
|
||||
if(--gradient->ref == 0)
|
||||
{
|
||||
free(gradient->stops.data);
|
||||
free(gradient);
|
||||
}
|
||||
}
|
||||
|
||||
int plutovg_gradient_get_reference_count(const plutovg_gradient_t* gradient)
|
||||
{
|
||||
if(gradient == NULL)
|
||||
return 0;
|
||||
|
||||
return gradient->ref;
|
||||
}
|
||||
|
||||
void plutovg_gradient_set_spread(plutovg_gradient_t* gradient, plutovg_spread_method_t spread)
|
||||
{
|
||||
gradient->spread = spread;
|
||||
}
|
||||
|
||||
plutovg_spread_method_t plutovg_gradient_get_spread(const plutovg_gradient_t* gradient)
|
||||
{
|
||||
return gradient->spread;
|
||||
}
|
||||
|
||||
void plutovg_gradient_set_matrix(plutovg_gradient_t* gradient, const plutovg_matrix_t* matrix)
|
||||
{
|
||||
gradient->matrix = *matrix;
|
||||
}
|
||||
|
||||
void plutovg_gradient_get_matrix(const plutovg_gradient_t* gradient, plutovg_matrix_t *matrix)
|
||||
{
|
||||
*matrix = gradient->matrix;
|
||||
}
|
||||
|
||||
void plutovg_gradient_add_stop_rgb(plutovg_gradient_t* gradient, double offset, double r, double g, double b)
|
||||
{
|
||||
plutovg_gradient_add_stop_rgba(gradient, offset, r, g, b, 1.0);
|
||||
}
|
||||
|
||||
void plutovg_gradient_add_stop_rgba(plutovg_gradient_t* gradient, double offset, double r, double g, double b, double a)
|
||||
{
|
||||
if(offset < 0.0) offset = 0.0;
|
||||
if(offset > 1.0) offset = 1.0;
|
||||
|
||||
plutovg_array_ensure(gradient->stops, 1);
|
||||
plutovg_gradient_stop_t* stops = gradient->stops.data;
|
||||
int nstops = gradient->stops.size;
|
||||
int i;
|
||||
for(i = 0;i < nstops;i++)
|
||||
{
|
||||
if(offset < stops[i].offset)
|
||||
{
|
||||
memmove(&stops[i+1], &stops[i], (size_t)(nstops - i) * sizeof(plutovg_gradient_stop_t));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
plutovg_gradient_stop_t* stop = &stops[i];
|
||||
stop->offset = offset;
|
||||
plutovg_color_init_rgba(&stop->color, r, g, b, a);
|
||||
gradient->stops.size += 1;
|
||||
}
|
||||
|
||||
void plutovg_gradient_add_stop_color(plutovg_gradient_t* gradient, double offset, const plutovg_color_t* color)
|
||||
{
|
||||
plutovg_gradient_add_stop_rgba(gradient, offset, color->r, color->g, color->b, color->a);
|
||||
}
|
||||
|
||||
void plutovg_gradient_add_stop(plutovg_gradient_t* gradient, const plutovg_gradient_stop_t* stop)
|
||||
{
|
||||
plutovg_gradient_add_stop_rgba(gradient, stop->offset, stop->color.r, stop->color.g, stop->color.b, stop->color.a);
|
||||
}
|
||||
|
||||
void plutovg_gradient_clear_stops(plutovg_gradient_t* gradient)
|
||||
{
|
||||
gradient->stops.size = 0;
|
||||
}
|
||||
|
||||
int plutovg_gradient_get_stop_count(const plutovg_gradient_t* gradient)
|
||||
{
|
||||
return gradient->stops.size;
|
||||
}
|
||||
|
||||
plutovg_gradient_stop_t* plutovg_gradient_get_stops(const plutovg_gradient_t* gradient)
|
||||
{
|
||||
return gradient->stops.data;
|
||||
}
|
||||
|
||||
plutovg_gradient_type_t plutovg_gradient_get_type(const plutovg_gradient_t* gradient)
|
||||
{
|
||||
return gradient->type;
|
||||
}
|
||||
|
||||
void plutovg_gradient_get_values_linear(const plutovg_gradient_t* gradient, double* x1, double* y1, double* x2, double* y2)
|
||||
{
|
||||
if(x1) *x1 = gradient->values[0];
|
||||
if(y1) *y1 = gradient->values[1];
|
||||
if(x2) *x2 = gradient->values[2];
|
||||
if(y2) *y2 = gradient->values[3];
|
||||
}
|
||||
|
||||
void plutovg_gradient_get_values_radial(const plutovg_gradient_t* gradient, double* cx, double* cy, double* cr, double* fx, double* fy, double* fr)
|
||||
{
|
||||
if(cx) *cx = gradient->values[0];
|
||||
if(cy) *cy = gradient->values[1];
|
||||
if(cr) *cr = gradient->values[2];
|
||||
if(fx) *fx = gradient->values[3];
|
||||
if(fy) *fy = gradient->values[4];
|
||||
if(fr) *fr = gradient->values[5];
|
||||
}
|
||||
|
||||
void plutovg_gradient_set_values_linear(plutovg_gradient_t* gradient, double x1, double y1, double x2, double y2)
|
||||
{
|
||||
gradient->values[0] = x1;
|
||||
gradient->values[1] = y1;
|
||||
gradient->values[2] = x2;
|
||||
gradient->values[3] = y2;
|
||||
}
|
||||
|
||||
void plutovg_gradient_set_values_radial(plutovg_gradient_t* gradient, double cx, double cy, double cr, double fx, double fy, double fr)
|
||||
{
|
||||
gradient->values[0] = cx;
|
||||
gradient->values[1] = cy;
|
||||
gradient->values[2] = cr;
|
||||
gradient->values[3] = fx;
|
||||
gradient->values[4] = fy;
|
||||
gradient->values[5] = fr;
|
||||
}
|
||||
|
||||
void plutovg_gradient_set_opacity(plutovg_gradient_t* gradient, double opacity)
|
||||
{
|
||||
gradient->opacity = CLAMP(opacity, 0.0, 1.0);
|
||||
}
|
||||
|
||||
double plutovg_gradient_get_opacity(const plutovg_gradient_t* gradient)
|
||||
{
|
||||
return gradient->opacity;
|
||||
}
|
||||
|
||||
plutovg_texture_t* plutovg_texture_create(plutovg_surface_t* surface)
|
||||
{
|
||||
plutovg_texture_t* texture = malloc(sizeof(plutovg_texture_t));
|
||||
texture->ref = 1;
|
||||
texture->type = plutovg_texture_type_plain;
|
||||
texture->surface = plutovg_surface_reference(surface);
|
||||
texture->opacity = 1.0;
|
||||
plutovg_matrix_init_identity(&texture->matrix);
|
||||
return texture;
|
||||
}
|
||||
|
||||
plutovg_texture_t* plutovg_texture_reference(plutovg_texture_t* texture)
|
||||
{
|
||||
if(texture == NULL)
|
||||
return NULL;
|
||||
|
||||
++texture->ref;
|
||||
return texture;
|
||||
}
|
||||
|
||||
void plutovg_texture_destroy(plutovg_texture_t* texture)
|
||||
{
|
||||
if(texture == NULL)
|
||||
return;
|
||||
|
||||
if(--texture->ref == 0)
|
||||
{
|
||||
plutovg_surface_destroy(texture->surface);
|
||||
free(texture);
|
||||
}
|
||||
}
|
||||
|
||||
int plutovg_texture_get_reference_count(const plutovg_texture_t* texture)
|
||||
{
|
||||
if(texture == NULL)
|
||||
return 0;
|
||||
|
||||
return texture->ref;
|
||||
}
|
||||
|
||||
void plutovg_texture_set_type(plutovg_texture_t* texture, plutovg_texture_type_t type)
|
||||
{
|
||||
texture->type = type;
|
||||
}
|
||||
|
||||
plutovg_texture_type_t plutovg_texture_get_type(const plutovg_texture_t* texture)
|
||||
{
|
||||
return texture->type;
|
||||
}
|
||||
|
||||
void plutovg_texture_set_matrix(plutovg_texture_t* texture, const plutovg_matrix_t* matrix)
|
||||
{
|
||||
texture->matrix = *matrix;
|
||||
}
|
||||
|
||||
void plutovg_texture_get_matrix(const plutovg_texture_t* texture, plutovg_matrix_t* matrix)
|
||||
{
|
||||
*matrix = texture->matrix;
|
||||
}
|
||||
|
||||
void plutovg_texture_set_surface(plutovg_texture_t* texture, plutovg_surface_t* surface)
|
||||
{
|
||||
surface = plutovg_surface_reference(surface);
|
||||
plutovg_surface_destroy(texture->surface);
|
||||
texture->surface = surface;
|
||||
}
|
||||
|
||||
plutovg_surface_t* plutovg_texture_get_surface(const plutovg_texture_t* texture)
|
||||
{
|
||||
return texture->surface;
|
||||
}
|
||||
|
||||
void plutovg_texture_set_opacity(plutovg_texture_t* texture, double opacity)
|
||||
{
|
||||
texture->opacity = CLAMP(opacity, 0.0, 1.0);
|
||||
}
|
||||
|
||||
double plutovg_texture_get_opacity(const plutovg_texture_t* texture)
|
||||
{
|
||||
return texture->opacity;
|
||||
}
|
||||
|
||||
plutovg_paint_t* plutovg_paint_create_rgb(double r, double g, double b)
|
||||
{
|
||||
return plutovg_paint_create_rgba(r, g, b, 1.0);
|
||||
}
|
||||
|
||||
plutovg_paint_t* plutovg_paint_create_rgba(double r, double g, double b, double a)
|
||||
{
|
||||
plutovg_paint_t* paint = malloc(sizeof(plutovg_paint_t));
|
||||
paint->ref = 1;
|
||||
paint->type = plutovg_paint_type_color;
|
||||
paint->color = malloc(sizeof(plutovg_color_t));
|
||||
plutovg_color_init_rgba(paint->color, r, g, b, a);
|
||||
return paint;
|
||||
}
|
||||
|
||||
plutovg_paint_t* plutovg_paint_create_linear(double x1, double y1, double x2, double y2)
|
||||
{
|
||||
plutovg_gradient_t* gradient = plutovg_gradient_create_linear(x1, y1, x2, y2);
|
||||
plutovg_paint_t* paint = plutovg_paint_create_gradient(gradient);
|
||||
plutovg_gradient_destroy(gradient);
|
||||
return paint;
|
||||
}
|
||||
|
||||
plutovg_paint_t* plutovg_paint_create_radial(double cx, double cy, double cr, double fx, double fy, double fr)
|
||||
{
|
||||
plutovg_gradient_t* gradient = plutovg_gradient_create_radial(cx, cy, cr, fx, fy, fr);
|
||||
plutovg_paint_t* paint = plutovg_paint_create_gradient(gradient);
|
||||
plutovg_gradient_destroy(gradient);
|
||||
return paint;
|
||||
}
|
||||
|
||||
plutovg_paint_t* plutovg_paint_create_for_surface(plutovg_surface_t* surface)
|
||||
{
|
||||
plutovg_texture_t* texture = plutovg_texture_create(surface);
|
||||
plutovg_paint_t* paint = plutovg_paint_create_texture(texture);
|
||||
plutovg_texture_destroy(texture);
|
||||
return paint;
|
||||
}
|
||||
|
||||
plutovg_paint_t* plutovg_paint_create_color(const plutovg_color_t* color)
|
||||
{
|
||||
return plutovg_paint_create_rgba(color->r, color->g, color->b, color->a);
|
||||
}
|
||||
|
||||
plutovg_paint_t* plutovg_paint_create_gradient(plutovg_gradient_t* gradient)
|
||||
{
|
||||
plutovg_paint_t* paint = malloc(sizeof(plutovg_paint_t));
|
||||
paint->ref = 1;
|
||||
paint->type = plutovg_paint_type_gradient;
|
||||
paint->gradient = plutovg_gradient_reference(gradient);
|
||||
return paint;
|
||||
}
|
||||
|
||||
plutovg_paint_t* plutovg_paint_create_texture(plutovg_texture_t* texture)
|
||||
{
|
||||
plutovg_paint_t* paint = malloc(sizeof(plutovg_paint_t));
|
||||
paint->ref = 1;
|
||||
paint->type = plutovg_paint_type_texture;
|
||||
paint->texture = plutovg_texture_reference(texture);
|
||||
return paint;
|
||||
}
|
||||
|
||||
plutovg_paint_t* plutovg_paint_reference(plutovg_paint_t* paint)
|
||||
{
|
||||
if(paint == NULL)
|
||||
return NULL;
|
||||
|
||||
++paint->ref;
|
||||
return paint;
|
||||
}
|
||||
|
||||
void plutovg_paint_destroy(plutovg_paint_t* paint)
|
||||
{
|
||||
if(paint == NULL)
|
||||
return;
|
||||
|
||||
if(--paint->ref == 0)
|
||||
{
|
||||
if(paint->type == plutovg_paint_type_color)
|
||||
free(paint->color);
|
||||
if(paint->type == plutovg_paint_type_gradient)
|
||||
plutovg_gradient_destroy(paint->gradient);
|
||||
if(paint->type == plutovg_paint_type_texture)
|
||||
plutovg_texture_destroy(paint->texture);
|
||||
free(paint);
|
||||
}
|
||||
}
|
||||
|
||||
int plutovg_paint_get_reference_count(const plutovg_paint_t* paint)
|
||||
{
|
||||
if(paint == NULL)
|
||||
return 0;
|
||||
|
||||
return paint->ref;
|
||||
}
|
||||
|
||||
plutovg_paint_type_t plutovg_paint_get_type(const plutovg_paint_t* paint)
|
||||
{
|
||||
return paint->type;
|
||||
}
|
||||
|
||||
plutovg_color_t* plutovg_paint_get_color(const plutovg_paint_t* paint)
|
||||
{
|
||||
return paint->type == plutovg_paint_type_color ? paint->color : NULL;
|
||||
}
|
||||
|
||||
plutovg_gradient_t* plutovg_paint_get_gradient(const plutovg_paint_t* paint)
|
||||
{
|
||||
return paint->type == plutovg_paint_type_gradient ? paint->gradient : NULL;
|
||||
}
|
||||
|
||||
plutovg_texture_t* plutovg_paint_get_texture(const plutovg_paint_t* paint)
|
||||
{
|
||||
return paint->type == plutovg_paint_type_texture ? paint->texture : NULL;
|
||||
}
|
||||
@@ -0,0 +1,179 @@
|
||||
#ifndef PLUTOVG_PRIVATE_H
|
||||
#define PLUTOVG_PRIVATE_H
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stddef.h>
|
||||
#include <string.h>
|
||||
#include <stdint.h>
|
||||
|
||||
#include "plutovg.h"
|
||||
/*
|
||||
struct plutovg_surface {
|
||||
int ref;
|
||||
unsigned char* data;
|
||||
int owndata;
|
||||
int width;
|
||||
int height;
|
||||
int stride;
|
||||
};
|
||||
*/
|
||||
struct plutovg_path {
|
||||
int ref;
|
||||
int contours;
|
||||
plutovg_point_t start;
|
||||
struct {
|
||||
plutovg_path_element_t* data;
|
||||
int size;
|
||||
int capacity;
|
||||
} elements;
|
||||
struct {
|
||||
plutovg_point_t* data;
|
||||
int size;
|
||||
int capacity;
|
||||
} points;
|
||||
};
|
||||
|
||||
struct plutovg_gradient {
|
||||
int ref;
|
||||
plutovg_gradient_type_t type;
|
||||
plutovg_spread_method_t spread;
|
||||
plutovg_matrix_t matrix;
|
||||
double values[6];
|
||||
double opacity;
|
||||
struct {
|
||||
plutovg_gradient_stop_t* data;
|
||||
int size;
|
||||
int capacity;
|
||||
} stops;
|
||||
};
|
||||
|
||||
struct plutovg_texture {
|
||||
int ref;
|
||||
plutovg_texture_type_t type;
|
||||
plutovg_surface_t* surface;
|
||||
plutovg_matrix_t matrix;
|
||||
double opacity;
|
||||
};
|
||||
|
||||
struct plutovg_paint {
|
||||
int ref;
|
||||
plutovg_paint_type_t type;
|
||||
union {
|
||||
plutovg_color_t* color;
|
||||
plutovg_gradient_t* gradient;
|
||||
plutovg_texture_t* texture;
|
||||
};
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
short x;
|
||||
short y;
|
||||
unsigned short len;
|
||||
unsigned char coverage;
|
||||
} plutovg_span_t;
|
||||
|
||||
typedef struct {
|
||||
struct {
|
||||
plutovg_span_t* data;
|
||||
int size;
|
||||
int capacity;
|
||||
} spans;
|
||||
|
||||
int x;
|
||||
int y;
|
||||
int w;
|
||||
int h;
|
||||
} plutovg_rle_t;
|
||||
|
||||
typedef struct {
|
||||
double offset;
|
||||
double* data;
|
||||
int size;
|
||||
} plutovg_dash_t;
|
||||
|
||||
typedef struct {
|
||||
double width;
|
||||
double miterlimit;
|
||||
plutovg_line_cap_t cap;
|
||||
plutovg_line_join_t join;
|
||||
plutovg_dash_t* dash;
|
||||
} plutovg_stroke_data_t;
|
||||
|
||||
typedef struct plutovg_state {
|
||||
plutovg_rle_t* clippath;
|
||||
plutovg_font_t* font;
|
||||
plutovg_paint_t* source;
|
||||
plutovg_matrix_t matrix;
|
||||
plutovg_fill_rule_t winding;
|
||||
plutovg_stroke_data_t stroke;
|
||||
plutovg_operator_t op;
|
||||
double opacity;
|
||||
struct plutovg_state* next;
|
||||
} plutovg_state_t;
|
||||
|
||||
struct plutovg {
|
||||
int ref;
|
||||
plutovg_surface_t* surface;
|
||||
plutovg_state_t* state;
|
||||
plutovg_path_t* path;
|
||||
plutovg_rle_t* rle;
|
||||
plutovg_rle_t* clippath;
|
||||
plutovg_rect_t clip;
|
||||
};
|
||||
|
||||
plutovg_rle_t* plutovg_rle_create(void);
|
||||
void plutovg_rle_destroy(plutovg_rle_t* rle);
|
||||
void plutovg_rle_rasterize(plutovg_rle_t* rle, const plutovg_path_t* path, const plutovg_matrix_t* matrix, const plutovg_rect_t* clip, const plutovg_stroke_data_t* stroke, plutovg_fill_rule_t winding);
|
||||
plutovg_rle_t* plutovg_rle_intersection(const plutovg_rle_t* a, const plutovg_rle_t* b);
|
||||
void plutovg_rle_intersect(plutovg_rle_t* rle, const plutovg_rle_t* clip);
|
||||
plutovg_rle_t* plutovg_rle_clone(const plutovg_rle_t* rle);
|
||||
void plutovg_rle_clear(plutovg_rle_t* rle);
|
||||
|
||||
plutovg_dash_t* plutovg_dash_create(double offset, const double* data, int size);
|
||||
plutovg_dash_t* plutovg_dash_clone(const plutovg_dash_t* dash);
|
||||
void plutovg_dash_destroy(plutovg_dash_t* dash);
|
||||
plutovg_path_t* plutovg_dash_path(const plutovg_dash_t* dash, const plutovg_path_t* path);
|
||||
|
||||
plutovg_state_t* plutovg_state_create(void);
|
||||
plutovg_state_t* plutovg_state_clone(const plutovg_state_t* state);
|
||||
void plutovg_state_destroy(plutovg_state_t* state);
|
||||
|
||||
void plutovg_blend(plutovg_t* pluto, const plutovg_rle_t* rle);
|
||||
void plutovg_blend_color(plutovg_t* pluto, const plutovg_rle_t* rle, const plutovg_color_t* color);
|
||||
void plutovg_blend_gradient(plutovg_t* pluto, const plutovg_rle_t* rle, const plutovg_gradient_t* gradient);
|
||||
void plutovg_blend_texture(plutovg_t* pluto, const plutovg_rle_t* rle, const plutovg_texture_t* texture);
|
||||
|
||||
#define SQRT2 1.41421356237309504880
|
||||
#define PI 3.14159265358979323846
|
||||
#define TWO_PI 6.28318530717958647693
|
||||
#define HALF_PI 1.57079632679489661923
|
||||
#define KAPPA 0.55228474983079339840
|
||||
|
||||
#define MIN(a, b) ((a) < (b) ? (a) : (b))
|
||||
#define MAX(a, b) ((a) > (b) ? (a) : (b))
|
||||
#define CLAMP(v, lo, hi) ((v) < (lo) ? (lo) : (hi) < (v) ? (hi) : (v))
|
||||
|
||||
#define plutovg_alpha(c) ((c) >> 24)
|
||||
#define plutovg_red(c) (((c) >> 16) & 0xff)
|
||||
#define plutovg_green(c) (((c) >> 8) & 0xff)
|
||||
#define plutovg_blue(c) (((c) >> 0) & 0xff)
|
||||
|
||||
#define plutovg_array_init(array) \
|
||||
do { \
|
||||
array.data = NULL; \
|
||||
array.size = 0; \
|
||||
array.capacity = 0; \
|
||||
} while(0)
|
||||
|
||||
#define plutovg_array_ensure(array, count) \
|
||||
do { \
|
||||
if(array.size + count > array.capacity) { \
|
||||
int capacity = array.size + count; \
|
||||
int newcapacity = array.capacity == 0 ? 8 : array.capacity; \
|
||||
while(newcapacity < capacity) { newcapacity *= 2; } \
|
||||
array.data = realloc(array.data, (size_t)newcapacity * sizeof(array.data[0])); \
|
||||
array.capacity = newcapacity; \
|
||||
} \
|
||||
} while(0)
|
||||
|
||||
#endif // PLUTOVG_PRIVATE_H
|
||||
+407
@@ -0,0 +1,407 @@
|
||||
#include "plutovg-private.h"
|
||||
|
||||
#include "sw_ft_raster.h"
|
||||
#include "sw_ft_stroker.h"
|
||||
#include "sw_ft_types.h"
|
||||
#include "sw_ft_math.h"
|
||||
|
||||
#include <math.h>
|
||||
#include <limits.h>
|
||||
|
||||
static SW_FT_Outline* sw_ft_outline_create(int points, int contours)
|
||||
{
|
||||
SW_FT_Outline* ft = malloc(sizeof(SW_FT_Outline));
|
||||
ft->points = malloc((size_t)(points + contours) * sizeof(SW_FT_Vector));
|
||||
ft->tags = malloc((size_t)(points + contours) * sizeof(char));
|
||||
ft->contours = malloc((size_t)contours * sizeof(short));
|
||||
ft->contours_flag = malloc((size_t)contours * sizeof(char));
|
||||
ft->n_points = ft->n_contours = 0;
|
||||
ft->flags = 0x0;
|
||||
return ft;
|
||||
}
|
||||
|
||||
static void sw_ft_outline_destroy(SW_FT_Outline* ft)
|
||||
{
|
||||
free(ft->points);
|
||||
free(ft->tags);
|
||||
free(ft->contours);
|
||||
free(ft->contours_flag);
|
||||
free(ft);
|
||||
}
|
||||
|
||||
#define FT_COORD(x) (SW_FT_Pos)((x) * 64)
|
||||
static void sw_ft_outline_move_to(SW_FT_Outline* ft, double x, double y)
|
||||
{
|
||||
ft->points[ft->n_points].x = FT_COORD(x);
|
||||
ft->points[ft->n_points].y = FT_COORD(y);
|
||||
ft->tags[ft->n_points] = SW_FT_CURVE_TAG_ON;
|
||||
if(ft->n_points)
|
||||
{
|
||||
ft->contours[ft->n_contours] = ft->n_points - 1;
|
||||
ft->n_contours++;
|
||||
}
|
||||
|
||||
ft->contours_flag[ft->n_contours] = 1;
|
||||
ft->n_points++;
|
||||
}
|
||||
|
||||
static void sw_ft_outline_line_to(SW_FT_Outline* ft, double x, double y)
|
||||
{
|
||||
ft->points[ft->n_points].x = FT_COORD(x);
|
||||
ft->points[ft->n_points].y = FT_COORD(y);
|
||||
ft->tags[ft->n_points] = SW_FT_CURVE_TAG_ON;
|
||||
ft->n_points++;
|
||||
}
|
||||
|
||||
static void sw_ft_outline_cubic_to(SW_FT_Outline* ft, double x1, double y1, double x2, double y2, double x3, double y3)
|
||||
{
|
||||
ft->points[ft->n_points].x = FT_COORD(x1);
|
||||
ft->points[ft->n_points].y = FT_COORD(y1);
|
||||
ft->tags[ft->n_points] = SW_FT_CURVE_TAG_CUBIC;
|
||||
ft->n_points++;
|
||||
|
||||
ft->points[ft->n_points].x = FT_COORD(x2);
|
||||
ft->points[ft->n_points].y = FT_COORD(y2);
|
||||
ft->tags[ft->n_points] = SW_FT_CURVE_TAG_CUBIC;
|
||||
ft->n_points++;
|
||||
|
||||
ft->points[ft->n_points].x = FT_COORD(x3);
|
||||
ft->points[ft->n_points].y = FT_COORD(y3);
|
||||
ft->tags[ft->n_points] = SW_FT_CURVE_TAG_ON;
|
||||
ft->n_points++;
|
||||
}
|
||||
|
||||
static void sw_ft_outline_close(SW_FT_Outline* ft)
|
||||
{
|
||||
ft->contours_flag[ft->n_contours] = 0;
|
||||
int index = ft->n_contours ? ft->contours[ft->n_contours - 1] + 1 : 0;
|
||||
if(index == ft->n_points)
|
||||
return;
|
||||
|
||||
ft->points[ft->n_points].x = ft->points[index].x;
|
||||
ft->points[ft->n_points].y = ft->points[index].y;
|
||||
ft->tags[ft->n_points] = SW_FT_CURVE_TAG_ON;
|
||||
ft->n_points++;
|
||||
}
|
||||
|
||||
static void sw_ft_outline_end(SW_FT_Outline* ft)
|
||||
{
|
||||
if(ft->n_points)
|
||||
{
|
||||
ft->contours[ft->n_contours] = ft->n_points - 1;
|
||||
ft->n_contours++;
|
||||
}
|
||||
}
|
||||
|
||||
static SW_FT_Outline* sw_ft_outline_convert(const plutovg_path_t* path, const plutovg_matrix_t* matrix)
|
||||
{
|
||||
SW_FT_Outline* outline = sw_ft_outline_create(path->points.size, path->contours);
|
||||
plutovg_path_element_t* elements = path->elements.data;
|
||||
plutovg_point_t* points = path->points.data;
|
||||
plutovg_point_t p[3];
|
||||
for(int i = 0;i < path->elements.size;i++)
|
||||
{
|
||||
switch(elements[i]) {
|
||||
case plutovg_path_element_move_to:
|
||||
plutovg_matrix_map_point(matrix, &points[0], &p[0]);
|
||||
sw_ft_outline_move_to(outline, p[0].x, p[0].y);
|
||||
points += 1;
|
||||
break;
|
||||
case plutovg_path_element_line_to:
|
||||
plutovg_matrix_map_point(matrix, &points[0], &p[0]);
|
||||
sw_ft_outline_line_to(outline, p[0].x, p[0].y);
|
||||
points += 1;
|
||||
break;
|
||||
case plutovg_path_element_cubic_to:
|
||||
plutovg_matrix_map_point(matrix, &points[0], &p[0]);
|
||||
plutovg_matrix_map_point(matrix, &points[1], &p[1]);
|
||||
plutovg_matrix_map_point(matrix, &points[2], &p[2]);
|
||||
sw_ft_outline_cubic_to(outline, p[0].x, p[0].y, p[1].x, p[1].y, p[2].x, p[2].y);
|
||||
points += 3;
|
||||
break;
|
||||
case plutovg_path_element_close:
|
||||
sw_ft_outline_close(outline);
|
||||
points += 1;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
sw_ft_outline_end(outline);
|
||||
return outline;
|
||||
}
|
||||
|
||||
static SW_FT_Outline* sw_ft_outline_convert_dash(const plutovg_path_t* path, const plutovg_matrix_t* matrix, const plutovg_dash_t* dash)
|
||||
{
|
||||
plutovg_path_t* dashed = plutovg_dash_path(dash, path);
|
||||
SW_FT_Outline* outline = sw_ft_outline_convert(dashed, matrix);
|
||||
plutovg_path_destroy(dashed);
|
||||
return outline;
|
||||
}
|
||||
|
||||
static void generation_callback(int count, const SW_FT_Span* spans, void* user)
|
||||
{
|
||||
plutovg_rle_t* rle = user;
|
||||
plutovg_array_ensure(rle->spans, count);
|
||||
plutovg_span_t* data = rle->spans.data + rle->spans.size;
|
||||
memcpy(data, spans, (size_t)count * sizeof(plutovg_span_t));
|
||||
rle->spans.size += count;
|
||||
}
|
||||
|
||||
static void bbox_callback(int x, int y, int w, int h, void* user)
|
||||
{
|
||||
plutovg_rle_t* rle = user;
|
||||
rle->x = x;
|
||||
rle->y = y;
|
||||
rle->w = w;
|
||||
rle->h = h;
|
||||
}
|
||||
|
||||
plutovg_rle_t* plutovg_rle_create(void)
|
||||
{
|
||||
plutovg_rle_t* rle = malloc(sizeof(plutovg_rle_t));
|
||||
plutovg_array_init(rle->spans);
|
||||
rle->x = 0;
|
||||
rle->y = 0;
|
||||
rle->w = 0;
|
||||
rle->h = 0;
|
||||
return rle;
|
||||
}
|
||||
|
||||
void plutovg_rle_destroy(plutovg_rle_t* rle)
|
||||
{
|
||||
if(rle == NULL)
|
||||
return;
|
||||
|
||||
free(rle->spans.data);
|
||||
free(rle);
|
||||
}
|
||||
|
||||
void plutovg_rle_rasterize(plutovg_rle_t* rle, const plutovg_path_t* path, const plutovg_matrix_t* matrix, const plutovg_rect_t* clip, const plutovg_stroke_data_t* stroke, plutovg_fill_rule_t winding)
|
||||
{
|
||||
SW_FT_Raster_Params params;
|
||||
params.flags = SW_FT_RASTER_FLAG_DIRECT | SW_FT_RASTER_FLAG_AA;
|
||||
params.gray_spans = generation_callback;
|
||||
params.bbox_cb = bbox_callback;
|
||||
params.user = rle;
|
||||
|
||||
if(clip)
|
||||
{
|
||||
params.flags |= SW_FT_RASTER_FLAG_CLIP;
|
||||
params.clip_box.xMin = (SW_FT_Pos)clip->x;
|
||||
params.clip_box.yMin = (SW_FT_Pos)clip->y;
|
||||
params.clip_box.xMax = (SW_FT_Pos)(clip->x + clip->w);
|
||||
params.clip_box.yMax = (SW_FT_Pos)(clip->y + clip->h);
|
||||
}
|
||||
|
||||
if(stroke)
|
||||
{
|
||||
SW_FT_Stroker_LineCap ftCap;
|
||||
SW_FT_Stroker_LineJoin ftJoin;
|
||||
SW_FT_Fixed ftWidth;
|
||||
SW_FT_Fixed ftMiterLimit;
|
||||
|
||||
plutovg_point_t p1 = {0, 0};
|
||||
plutovg_point_t p2 = {SQRT2, SQRT2};
|
||||
|
||||
plutovg_matrix_map_point(matrix, &p1, &p1);
|
||||
plutovg_matrix_map_point(matrix, &p2, &p2);
|
||||
|
||||
double dx = p2.x - p1.x;
|
||||
double dy = p2.y - p1.y;
|
||||
|
||||
double scale = sqrt(dx*dx + dy*dy) / 2.0;
|
||||
double radius = stroke->width / 2.0;
|
||||
|
||||
ftWidth = (SW_FT_Fixed)(radius * scale * (1 << 6));
|
||||
ftMiterLimit = (SW_FT_Fixed)(stroke->miterlimit * (1 << 16));
|
||||
|
||||
switch(stroke->cap) {
|
||||
case plutovg_line_cap_square:
|
||||
ftCap = SW_FT_STROKER_LINECAP_SQUARE;
|
||||
break;
|
||||
case plutovg_line_cap_round:
|
||||
ftCap = SW_FT_STROKER_LINECAP_ROUND;
|
||||
break;
|
||||
default:
|
||||
ftCap = SW_FT_STROKER_LINECAP_BUTT;
|
||||
break;
|
||||
}
|
||||
|
||||
switch(stroke->join) {
|
||||
case plutovg_line_join_bevel:
|
||||
ftJoin = SW_FT_STROKER_LINEJOIN_BEVEL;
|
||||
break;
|
||||
case plutovg_line_join_round:
|
||||
ftJoin = SW_FT_STROKER_LINEJOIN_ROUND;
|
||||
break;
|
||||
default:
|
||||
ftJoin = SW_FT_STROKER_LINEJOIN_MITER_FIXED;
|
||||
break;
|
||||
}
|
||||
|
||||
SW_FT_Outline* outline = stroke->dash ? sw_ft_outline_convert_dash(path, matrix, stroke->dash) : sw_ft_outline_convert(path, matrix);
|
||||
SW_FT_Stroker stroker;
|
||||
SW_FT_Stroker_New(&stroker);
|
||||
SW_FT_Stroker_Set(stroker, ftWidth, ftCap, ftJoin, ftMiterLimit);
|
||||
SW_FT_Stroker_ParseOutline(stroker, outline);
|
||||
|
||||
SW_FT_UInt points;
|
||||
SW_FT_UInt contours;
|
||||
SW_FT_Stroker_GetCounts(stroker, &points, &contours);
|
||||
|
||||
SW_FT_Outline* strokeOutline = sw_ft_outline_create((int)points, (int)contours);
|
||||
SW_FT_Stroker_Export(stroker, strokeOutline);
|
||||
SW_FT_Stroker_Done(stroker);
|
||||
|
||||
strokeOutline->flags = SW_FT_OUTLINE_NONE;
|
||||
params.source = strokeOutline;
|
||||
sw_ft_grays_raster.raster_render(NULL, ¶ms);
|
||||
sw_ft_outline_destroy(outline);
|
||||
sw_ft_outline_destroy(strokeOutline);
|
||||
}
|
||||
else
|
||||
{
|
||||
SW_FT_Outline* outline = sw_ft_outline_convert(path, matrix);
|
||||
outline->flags = winding == plutovg_fill_rule_even_odd ? SW_FT_OUTLINE_EVEN_ODD_FILL : SW_FT_OUTLINE_NONE;
|
||||
params.source = outline;
|
||||
sw_ft_grays_raster.raster_render(NULL, ¶ms);
|
||||
sw_ft_outline_destroy(outline);
|
||||
}
|
||||
}
|
||||
|
||||
#define DIV255(x) (((x) + ((x) >> 8) + 0x80) >> 8)
|
||||
plutovg_rle_t* plutovg_rle_intersection(const plutovg_rle_t* a, const plutovg_rle_t* b)
|
||||
{
|
||||
plutovg_rle_t* result = malloc(sizeof(plutovg_rle_t));
|
||||
plutovg_array_init(result->spans);
|
||||
plutovg_array_ensure(result->spans, MAX(a->spans.size, b->spans.size));
|
||||
|
||||
plutovg_span_t* a_spans = a->spans.data;
|
||||
plutovg_span_t* a_end = a_spans + a->spans.size;
|
||||
|
||||
plutovg_span_t* b_spans = b->spans.data;
|
||||
plutovg_span_t* b_end = b_spans + b->spans.size;
|
||||
|
||||
while(a_spans < a_end && b_spans < b_end)
|
||||
{
|
||||
if(b_spans->y > a_spans->y)
|
||||
{
|
||||
++a_spans;
|
||||
continue;
|
||||
}
|
||||
|
||||
if(a_spans->y != b_spans->y)
|
||||
{
|
||||
++b_spans;
|
||||
continue;
|
||||
}
|
||||
|
||||
int ax1 = a_spans->x;
|
||||
int ax2 = ax1 + a_spans->len;
|
||||
int bx1 = b_spans->x;
|
||||
int bx2 = bx1 + b_spans->len;
|
||||
|
||||
if(bx1 < ax1 && bx2 < ax1)
|
||||
{
|
||||
++b_spans;
|
||||
continue;
|
||||
}
|
||||
|
||||
if(ax1 < bx1 && ax2 < bx1)
|
||||
{
|
||||
++a_spans;
|
||||
continue;
|
||||
}
|
||||
|
||||
int x = MAX(ax1, bx1);
|
||||
int len = MIN(ax2, bx2) - x;
|
||||
if(len)
|
||||
{
|
||||
plutovg_span_t* span = result->spans.data + result->spans.size;
|
||||
if(span) {
|
||||
span->x = (short)x;
|
||||
span->len = (uint16_t)len;
|
||||
span->y = a_spans->y;
|
||||
span->coverage = DIV255(a_spans->coverage * b_spans->coverage);
|
||||
}
|
||||
result->spans.size += 1;
|
||||
}
|
||||
|
||||
if(ax2 < bx2)
|
||||
{
|
||||
++a_spans;
|
||||
}
|
||||
else
|
||||
{
|
||||
++b_spans;
|
||||
}
|
||||
}
|
||||
|
||||
if(result->spans.size == 0)
|
||||
{
|
||||
result->x = 0;
|
||||
result->y = 0;
|
||||
result->w = 0;
|
||||
result->h = 0;
|
||||
return result;
|
||||
}
|
||||
|
||||
plutovg_span_t* spans = result->spans.data;
|
||||
int x1 = INT_MAX;
|
||||
int y1 = spans[0].y;
|
||||
int x2 = 0;
|
||||
int y2 = spans[result->spans.size - 1].y;
|
||||
for(int i = 0;i < result->spans.size;i++)
|
||||
{
|
||||
if(spans[i].x < x1) x1 = spans[i].x;
|
||||
if(spans[i].x + spans[i].len > x2) x2 = spans[i].x + spans[i].len;
|
||||
}
|
||||
|
||||
result->x = x1;
|
||||
result->y = y1;
|
||||
result->w = x2 - x1;
|
||||
result->h = y2 - y1 + 1;
|
||||
return result;
|
||||
}
|
||||
|
||||
void plutovg_rle_intersect(plutovg_rle_t* rle, const plutovg_rle_t* clip)
|
||||
{
|
||||
if(rle == NULL || clip == NULL)
|
||||
return;
|
||||
|
||||
plutovg_rle_t* result = plutovg_rle_intersection(rle, clip);
|
||||
plutovg_array_ensure(rle->spans, result->spans.size);
|
||||
memcpy(rle->spans.data, result->spans.data, (size_t)result->spans.size * sizeof(plutovg_span_t));
|
||||
rle->spans.size = result->spans.size;
|
||||
rle->x = result->x;
|
||||
rle->y = result->y;
|
||||
rle->w = result->w;
|
||||
rle->h = result->h;
|
||||
plutovg_rle_destroy(result);
|
||||
}
|
||||
|
||||
plutovg_rle_t* plutovg_rle_clone(const plutovg_rle_t* rle)
|
||||
{
|
||||
if(rle == NULL)
|
||||
return NULL;
|
||||
|
||||
plutovg_rle_t* result = malloc(sizeof(plutovg_rle_t));
|
||||
plutovg_array_init(result->spans);
|
||||
plutovg_array_ensure(result->spans, rle->spans.size);
|
||||
memcpy(result->spans.data, rle->spans.data, (size_t)rle->spans.size * sizeof(plutovg_span_t));
|
||||
result->spans.size = rle->spans.size;
|
||||
result->x = rle->x;
|
||||
result->y = rle->y;
|
||||
result->w = rle->w;
|
||||
result->h = rle->h;
|
||||
return result;
|
||||
}
|
||||
|
||||
void plutovg_rle_clear(plutovg_rle_t* rle)
|
||||
{
|
||||
rle->spans.size = 0;
|
||||
rle->x = 0;
|
||||
rle->y = 0;
|
||||
rle->w = 0;
|
||||
rle->h = 0;
|
||||
}
|
||||
+654
@@ -0,0 +1,654 @@
|
||||
#define STB_IMAGE_WRITE_IMPLEMENTATION
|
||||
#include "plutovg-private.h"
|
||||
|
||||
plutovg_surface_t* plutovg_surface_create(int width, int height)
|
||||
{
|
||||
plutovg_surface_t* surface = malloc(sizeof(plutovg_surface_t));
|
||||
surface->ref = 1;
|
||||
surface->owndata = 1;
|
||||
surface->data = calloc(1, (size_t)(width * height * 4));
|
||||
surface->width = width;
|
||||
surface->height = height;
|
||||
surface->stride = width * 4;
|
||||
return surface;
|
||||
}
|
||||
|
||||
plutovg_surface_t* plutovg_surface_create_for_data(unsigned char* data, int width, int height, int stride)
|
||||
{
|
||||
plutovg_surface_t* surface = malloc(sizeof(plutovg_surface_t));
|
||||
surface->ref = 1;
|
||||
surface->owndata = 0;
|
||||
surface->data = data;
|
||||
surface->width = width;
|
||||
surface->height = height;
|
||||
surface->stride = stride;
|
||||
return surface;
|
||||
}
|
||||
|
||||
plutovg_surface_t* plutovg_surface_reference(plutovg_surface_t* surface)
|
||||
{
|
||||
if(surface == NULL)
|
||||
return NULL;
|
||||
|
||||
++surface->ref;
|
||||
return surface;
|
||||
}
|
||||
|
||||
void plutovg_surface_destroy(plutovg_surface_t* surface)
|
||||
{
|
||||
if(surface == NULL)
|
||||
return;
|
||||
|
||||
if(--surface->ref == 0)
|
||||
{
|
||||
if(surface->owndata)
|
||||
free(surface->data);
|
||||
free(surface);
|
||||
}
|
||||
}
|
||||
|
||||
int plutovg_surface_get_reference_count(const plutovg_surface_t* surface)
|
||||
{
|
||||
if(surface == NULL)
|
||||
return 0;
|
||||
|
||||
return surface->ref;
|
||||
}
|
||||
|
||||
unsigned char* plutovg_surface_get_data(const plutovg_surface_t* surface)
|
||||
{
|
||||
return surface->data;
|
||||
}
|
||||
|
||||
int plutovg_surface_get_width(const plutovg_surface_t* surface)
|
||||
{
|
||||
return surface->width;
|
||||
}
|
||||
|
||||
int plutovg_surface_get_height(const plutovg_surface_t* surface)
|
||||
{
|
||||
return surface->height;
|
||||
}
|
||||
|
||||
int plutovg_surface_get_stride(const plutovg_surface_t* surface)
|
||||
{
|
||||
return surface->stride;
|
||||
}
|
||||
/*
|
||||
void plutovg_surface_write_to_png(const plutovg_surface_t* surface, const char* filename)
|
||||
{
|
||||
unsigned char* data = surface->data;
|
||||
int width = surface->width;
|
||||
int height = surface->height;
|
||||
int stride = surface->stride;
|
||||
unsigned char* image = calloc(1, (size_t)(stride * height));
|
||||
for(int y = 0;y < height;y++)
|
||||
{
|
||||
const uint32_t* src = (uint32_t*)(data + stride * y);
|
||||
uint32_t* dst = (uint32_t*)(image + stride * y);
|
||||
for(int x = 0;x < width;x++)
|
||||
{
|
||||
uint32_t a = src[x] >> 24;
|
||||
if(a == 0)
|
||||
continue;
|
||||
|
||||
uint32_t r = (((src[x] >> 16) & 0xff) * 255) / a;
|
||||
uint32_t g = (((src[x] >> 8) & 0xff) * 255) / a;
|
||||
uint32_t b = (((src[x] >> 0) & 0xff) * 255) / a;
|
||||
|
||||
dst[x] = (a << 24) | (b << 16) | (g << 8) | r;
|
||||
}
|
||||
}
|
||||
|
||||
stbi_write_png(filename, width, height, 4, image, stride);
|
||||
free(image);
|
||||
}
|
||||
*/
|
||||
|
||||
plutovg_state_t* plutovg_state_create(void)
|
||||
{
|
||||
plutovg_state_t* state = malloc(sizeof(plutovg_state_t));
|
||||
state->clippath = NULL;
|
||||
state->font = NULL;
|
||||
state->source = plutovg_paint_create_rgb(0, 0, 0);
|
||||
plutovg_matrix_init_identity(&state->matrix);
|
||||
state->winding = plutovg_fill_rule_non_zero;
|
||||
state->stroke.width = 1.0;
|
||||
state->stroke.miterlimit = 4.0;
|
||||
state->stroke.cap = plutovg_line_cap_butt;
|
||||
state->stroke.join = plutovg_line_join_miter;
|
||||
state->stroke.dash = NULL;
|
||||
state->op = plutovg_operator_src_over;
|
||||
state->opacity = 1.0;
|
||||
state->next = NULL;
|
||||
return state;
|
||||
}
|
||||
|
||||
plutovg_state_t* plutovg_state_clone(const plutovg_state_t* state)
|
||||
{
|
||||
plutovg_state_t* newstate = malloc(sizeof(plutovg_state_t));
|
||||
newstate->clippath = plutovg_rle_clone(state->clippath);
|
||||
newstate->font = plutovg_font_reference(state->font); /** FIXME: clone!!?**/
|
||||
newstate->source = plutovg_paint_reference(state->source); /** FIXME: clone!!?**/
|
||||
newstate->matrix = state->matrix;
|
||||
newstate->winding = state->winding;
|
||||
newstate->stroke.width = state->stroke.width;
|
||||
newstate->stroke.miterlimit = state->stroke.miterlimit;
|
||||
newstate->stroke.cap = state->stroke.cap;
|
||||
newstate->stroke.join = state->stroke.join;
|
||||
newstate->stroke.dash = plutovg_dash_clone(state->stroke.dash);
|
||||
newstate->op = state->op;
|
||||
newstate->opacity = state->opacity;
|
||||
newstate->next = NULL;
|
||||
return newstate;
|
||||
}
|
||||
|
||||
void plutovg_state_destroy(plutovg_state_t* state)
|
||||
{
|
||||
plutovg_rle_destroy(state->clippath);
|
||||
plutovg_font_destroy(state->font);
|
||||
plutovg_paint_destroy(state->source);
|
||||
plutovg_dash_destroy(state->stroke.dash);
|
||||
free(state);
|
||||
}
|
||||
|
||||
plutovg_t* plutovg_create(plutovg_surface_t* surface)
|
||||
{
|
||||
plutovg_t* pluto = malloc(sizeof(plutovg_t));
|
||||
pluto->ref = 1;
|
||||
pluto->surface = plutovg_surface_reference(surface);
|
||||
pluto->state = plutovg_state_create();
|
||||
pluto->path = plutovg_path_create();
|
||||
pluto->rle = plutovg_rle_create();
|
||||
pluto->clippath = NULL;
|
||||
plutovg_rect_init(&pluto->clip, 0, 0, surface->width, surface->height);
|
||||
return pluto;
|
||||
}
|
||||
|
||||
plutovg_t* plutovg_reference(plutovg_t* pluto)
|
||||
{
|
||||
if(pluto == NULL)
|
||||
return NULL;
|
||||
|
||||
++pluto->ref;
|
||||
return pluto;
|
||||
}
|
||||
|
||||
void plutovg_destroy(plutovg_t* pluto)
|
||||
{
|
||||
if(pluto == NULL)
|
||||
return;
|
||||
|
||||
if(--pluto->ref == 0)
|
||||
{
|
||||
while(pluto->state)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
pluto->state = state->next;
|
||||
plutovg_state_destroy(state);
|
||||
}
|
||||
|
||||
plutovg_surface_destroy(pluto->surface);
|
||||
plutovg_path_destroy(pluto->path);
|
||||
plutovg_rle_destroy(pluto->rle);
|
||||
plutovg_rle_destroy(pluto->clippath);
|
||||
free(pluto);
|
||||
}
|
||||
}
|
||||
|
||||
int plutovg_get_reference_count(const plutovg_t* pluto)
|
||||
{
|
||||
if(pluto == NULL)
|
||||
return 0;
|
||||
|
||||
return pluto->ref;
|
||||
}
|
||||
|
||||
void plutovg_save(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_state_t* newstate = plutovg_state_clone(pluto->state);
|
||||
newstate->next = pluto->state;
|
||||
pluto->state = newstate;
|
||||
}
|
||||
|
||||
void plutovg_restore(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_state_t* oldstate = pluto->state;
|
||||
pluto->state = oldstate->next;
|
||||
plutovg_state_destroy(oldstate);
|
||||
}
|
||||
|
||||
void plutovg_set_source_rgb(plutovg_t* pluto, double r, double g, double b)
|
||||
{
|
||||
plutovg_set_source_rgba(pluto, r, g, b, 1.0);
|
||||
}
|
||||
|
||||
void plutovg_set_source_rgba(plutovg_t* pluto, double r, double g, double b, double a)
|
||||
{
|
||||
plutovg_paint_t* source = plutovg_paint_create_rgba(r, g, b, a);
|
||||
plutovg_set_source(pluto, source);
|
||||
plutovg_paint_destroy(source);
|
||||
}
|
||||
|
||||
void plutovg_set_source_surface(plutovg_t* pluto, plutovg_surface_t* surface, double x, double y)
|
||||
{
|
||||
plutovg_paint_t* source = plutovg_paint_create_for_surface(surface);
|
||||
plutovg_texture_t* texture = plutovg_paint_get_texture(source);
|
||||
plutovg_matrix_t matrix;
|
||||
plutovg_matrix_init_translate(&matrix, x, y);
|
||||
plutovg_texture_set_matrix(texture, &matrix);
|
||||
plutovg_set_source(pluto, source);
|
||||
plutovg_paint_destroy(source);
|
||||
}
|
||||
|
||||
void plutovg_set_source_color(plutovg_t* pluto, const plutovg_color_t* color)
|
||||
{
|
||||
plutovg_set_source_rgba(pluto, color->r, color->g, color->b, color->a);
|
||||
}
|
||||
|
||||
void plutovg_set_source_gradient(plutovg_t* pluto, plutovg_gradient_t* gradient)
|
||||
{
|
||||
plutovg_paint_t* source = plutovg_paint_create_gradient(gradient);
|
||||
plutovg_set_source(pluto, source);
|
||||
plutovg_paint_destroy(source);
|
||||
}
|
||||
|
||||
void plutovg_set_source_texture(plutovg_t* pluto, plutovg_texture_t* texture)
|
||||
{
|
||||
plutovg_paint_t* source = plutovg_paint_create_texture(texture);
|
||||
plutovg_set_source(pluto, source);
|
||||
plutovg_paint_destroy(source);
|
||||
}
|
||||
|
||||
void plutovg_set_source(plutovg_t* pluto, plutovg_paint_t* source)
|
||||
{
|
||||
source = plutovg_paint_reference(source);
|
||||
plutovg_paint_destroy(pluto->state->source);
|
||||
pluto->state->source = source;
|
||||
}
|
||||
|
||||
plutovg_paint_t* plutovg_get_source(const plutovg_t* pluto)
|
||||
{
|
||||
return pluto->state->source;
|
||||
}
|
||||
|
||||
void plutovg_set_operator(plutovg_t* pluto, plutovg_operator_t op)
|
||||
{
|
||||
pluto->state->op = op;
|
||||
}
|
||||
|
||||
void plutovg_set_opacity(plutovg_t* pluto, double opacity)
|
||||
{
|
||||
pluto->state->opacity = CLAMP(opacity, 0.0, 1.0);
|
||||
}
|
||||
|
||||
void plutovg_set_fill_rule(plutovg_t* pluto, plutovg_fill_rule_t winding)
|
||||
{
|
||||
pluto->state->winding = winding;
|
||||
}
|
||||
|
||||
plutovg_operator_t plutovg_get_operator(const plutovg_t* pluto)
|
||||
{
|
||||
return pluto->state->op;
|
||||
}
|
||||
|
||||
double plutovg_get_opacity(const plutovg_t* pluto)
|
||||
{
|
||||
return pluto->state->opacity;
|
||||
}
|
||||
|
||||
plutovg_fill_rule_t plutovg_get_fill_rule(const plutovg_t* pluto)
|
||||
{
|
||||
return pluto->state->winding;
|
||||
}
|
||||
|
||||
void plutovg_set_line_width(plutovg_t* pluto, double width)
|
||||
{
|
||||
pluto->state->stroke.width = width;
|
||||
}
|
||||
|
||||
void plutovg_set_line_cap(plutovg_t* pluto, plutovg_line_cap_t cap)
|
||||
{
|
||||
pluto->state->stroke.cap = cap;
|
||||
}
|
||||
|
||||
void plutovg_set_line_join(plutovg_t* pluto, plutovg_line_join_t join)
|
||||
{
|
||||
pluto->state->stroke.join = join;
|
||||
}
|
||||
|
||||
void plutovg_set_miter_limit(plutovg_t* pluto, double limit)
|
||||
{
|
||||
pluto->state->stroke.miterlimit = limit;
|
||||
}
|
||||
|
||||
void plutovg_set_dash(plutovg_t* pluto, double offset, const double* data, int size)
|
||||
{
|
||||
plutovg_dash_destroy(pluto->state->stroke.dash);
|
||||
pluto->state->stroke.dash = plutovg_dash_create(offset, data, size);
|
||||
}
|
||||
|
||||
double plutovg_get_line_width(const plutovg_t* pluto)
|
||||
{
|
||||
return pluto->state->stroke.width;
|
||||
}
|
||||
|
||||
plutovg_line_cap_t plutovg_get_line_cap(const plutovg_t* pluto)
|
||||
{
|
||||
return pluto->state->stroke.cap;
|
||||
}
|
||||
|
||||
plutovg_line_join_t plutovg_get_line_join(const plutovg_t* pluto)
|
||||
{
|
||||
return pluto->state->stroke.join;
|
||||
}
|
||||
|
||||
double plutovg_get_miter_limit(const plutovg_t* pluto)
|
||||
{
|
||||
return pluto->state->stroke.miterlimit;
|
||||
}
|
||||
|
||||
double plutovg_get_dash_offset(const plutovg_t* pluto)
|
||||
{
|
||||
plutovg_stroke_data_t* stroke = &pluto->state->stroke;
|
||||
return stroke->dash ? stroke->dash->offset : 0.0;
|
||||
}
|
||||
|
||||
const double* plutovg_get_dash_data(const plutovg_t* pluto)
|
||||
{
|
||||
plutovg_stroke_data_t* stroke = &pluto->state->stroke;
|
||||
return stroke->dash ? stroke->dash->data : NULL;
|
||||
}
|
||||
|
||||
int plutovg_get_dash_count(const plutovg_t* pluto)
|
||||
{
|
||||
plutovg_stroke_data_t* stroke = &pluto->state->stroke;
|
||||
return stroke->dash ? stroke->dash->size : 0;
|
||||
}
|
||||
|
||||
void plutovg_translate(plutovg_t* pluto, double x, double y)
|
||||
{
|
||||
plutovg_matrix_translate(&pluto->state->matrix, x, y);
|
||||
}
|
||||
|
||||
void plutovg_scale(plutovg_t* pluto, double x, double y)
|
||||
{
|
||||
plutovg_matrix_scale(&pluto->state->matrix, x, y);
|
||||
}
|
||||
|
||||
void plutovg_rotate(plutovg_t* pluto, double radians)
|
||||
{
|
||||
plutovg_matrix_rotate(&pluto->state->matrix, radians);
|
||||
}
|
||||
|
||||
void plutovg_transform(plutovg_t* pluto, const plutovg_matrix_t* matrix)
|
||||
{
|
||||
plutovg_matrix_multiply(&pluto->state->matrix, matrix, &pluto->state->matrix);
|
||||
}
|
||||
|
||||
void plutovg_set_matrix(plutovg_t* pluto, const plutovg_matrix_t* matrix)
|
||||
{
|
||||
pluto->state->matrix = *matrix;
|
||||
}
|
||||
|
||||
void plutovg_identity_matrix(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_matrix_init_identity(&pluto->state->matrix);
|
||||
}
|
||||
|
||||
void plutovg_get_matrix(const plutovg_t* pluto, plutovg_matrix_t* matrix)
|
||||
{
|
||||
*matrix = pluto->state->matrix;
|
||||
}
|
||||
|
||||
void plutovg_move_to(plutovg_t* pluto, double x, double y)
|
||||
{
|
||||
plutovg_path_move_to(pluto->path, x, y);
|
||||
}
|
||||
|
||||
void plutovg_line_to(plutovg_t* pluto, double x, double y)
|
||||
{
|
||||
plutovg_path_line_to(pluto->path, x, y);
|
||||
}
|
||||
|
||||
void plutovg_quad_to(plutovg_t* pluto, double x1, double y1, double x2, double y2)
|
||||
{
|
||||
plutovg_path_quad_to(pluto->path, x1, y1, x2, y2);
|
||||
}
|
||||
|
||||
void plutovg_cubic_to(plutovg_t* pluto, double x1, double y1, double x2, double y2, double x3, double y3)
|
||||
{
|
||||
plutovg_path_cubic_to(pluto->path, x1, y1, x2, y2, x3, y3);
|
||||
}
|
||||
|
||||
void plutovg_rel_move_to(plutovg_t* pluto, double x, double y)
|
||||
{
|
||||
plutovg_path_rel_move_to(pluto->path, x, y);
|
||||
}
|
||||
|
||||
void plutovg_rel_line_to(plutovg_t* pluto, double x, double y)
|
||||
{
|
||||
plutovg_path_rel_line_to(pluto->path, x, y);
|
||||
}
|
||||
|
||||
void plutovg_rel_quad_to(plutovg_t* pluto, double x1, double y1, double x2, double y2)
|
||||
{
|
||||
plutovg_path_rel_quad_to(pluto->path, x1, y1, x2, y2);
|
||||
}
|
||||
|
||||
void plutovg_rel_cubic_to(plutovg_t* pluto, double x1, double y1, double x2, double y2, double x3, double y3)
|
||||
{
|
||||
plutovg_path_rel_cubic_to(pluto->path, x1, y1, x2, y2, x3, y3);
|
||||
}
|
||||
|
||||
void plutovg_rect(plutovg_t* pluto, double x, double y, double w, double h)
|
||||
{
|
||||
plutovg_path_add_rect(pluto->path, x, y, w, h);
|
||||
}
|
||||
|
||||
void plutovg_round_rect(plutovg_t* pluto, double x, double y, double w, double h, double rx, double ry)
|
||||
{
|
||||
plutovg_path_add_round_rect(pluto->path, x, y, w, h, rx, ry);
|
||||
}
|
||||
|
||||
void plutovg_ellipse(plutovg_t* pluto, double cx, double cy, double rx, double ry)
|
||||
{
|
||||
plutovg_path_add_ellipse(pluto->path, cx, cy, rx, ry);
|
||||
}
|
||||
|
||||
void plutovg_circle(plutovg_t* pluto, double cx, double cy, double r)
|
||||
{
|
||||
plutovg_ellipse(pluto, cx, cy, r, r);
|
||||
}
|
||||
|
||||
void plutovg_arc(plutovg_t* pluto, double cx, double cy, double r, double a0, double a1, int ccw)
|
||||
{
|
||||
plutovg_path_add_arc(pluto->path, cx, cy, r, a0, a1, ccw);
|
||||
}
|
||||
|
||||
void plutovg_add_path(plutovg_t* pluto, const plutovg_path_t* path)
|
||||
{
|
||||
plutovg_path_add_path(pluto->path, path, NULL);
|
||||
}
|
||||
|
||||
void plutovg_new_path(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_path_clear(pluto->path);
|
||||
}
|
||||
|
||||
void plutovg_close_path(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_path_close(pluto->path);
|
||||
}
|
||||
|
||||
void plutovg_get_current_point(const plutovg_t* pluto, double* x, double* y)
|
||||
{
|
||||
plutovg_path_get_current_point(pluto->path, x, y);
|
||||
}
|
||||
|
||||
plutovg_path_t* plutovg_get_path(const plutovg_t* pluto)
|
||||
{
|
||||
return pluto->path;
|
||||
}
|
||||
|
||||
void plutovg_set_font(plutovg_t* pluto, plutovg_font_t* font)
|
||||
{
|
||||
font = plutovg_font_reference(font);
|
||||
plutovg_font_destroy(pluto->state->font);
|
||||
pluto->state->font = font;
|
||||
}
|
||||
|
||||
void plutovg_set_font_size(plutovg_t* pluto, double size)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
if(state->font == NULL)
|
||||
return;
|
||||
|
||||
plutovg_font_set_size(state->font, size);
|
||||
}
|
||||
|
||||
plutovg_font_t* plutovg_get_font(const plutovg_t* pluto)
|
||||
{
|
||||
return pluto->state->font;
|
||||
}
|
||||
|
||||
double plutovg_get_font_size(const plutovg_t* pluto)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
if(state->font == NULL)
|
||||
return 0.0;
|
||||
|
||||
return plutovg_font_get_size(state->font);
|
||||
}
|
||||
|
||||
void plutovg_char(plutovg_t* pluto, int ch, double x, double y)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
if(state->font == NULL)
|
||||
return;
|
||||
|
||||
plutovg_matrix_t matrix;
|
||||
plutovg_matrix_init_translate(&matrix, x, y);
|
||||
plutovg_path_t* path = plutovg_font_get_char_path(state->font, ch);
|
||||
plutovg_path_add_path(pluto->path, path, &matrix);
|
||||
plutovg_path_destroy(path);
|
||||
}
|
||||
|
||||
void plutovg_text(plutovg_t* pluto, const char* utf8, double x, double y)
|
||||
{
|
||||
plutovg_textn(pluto, utf8, (int)strlen(utf8), x, y);
|
||||
}
|
||||
|
||||
void plutovg_textn(plutovg_t* pluto, const char* utf8, int size, double x, double y)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
if(state->font == NULL)
|
||||
return;
|
||||
|
||||
plutovg_matrix_t matrix;
|
||||
plutovg_matrix_init_translate(&matrix, x, y);
|
||||
plutovg_path_t* path = plutovg_font_get_textn_path(state->font, utf8, size);
|
||||
plutovg_path_add_path(pluto->path, path, &matrix);
|
||||
plutovg_path_destroy(path);
|
||||
}
|
||||
|
||||
void plutovg_fill(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_fill_preserve(pluto);
|
||||
plutovg_new_path(pluto);
|
||||
}
|
||||
|
||||
void plutovg_stroke(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_stroke_preserve(pluto);
|
||||
plutovg_new_path(pluto);
|
||||
}
|
||||
|
||||
void plutovg_clip(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_clip_preserve(pluto);
|
||||
plutovg_new_path(pluto);
|
||||
}
|
||||
|
||||
void plutovg_paint(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
if(state->clippath == NULL && pluto->clippath == NULL)
|
||||
{
|
||||
plutovg_path_t* path = plutovg_path_create();
|
||||
plutovg_path_add_rect(path, pluto->clip.x, pluto->clip.y, pluto->clip.w, pluto->clip.h);
|
||||
plutovg_matrix_t matrix;
|
||||
plutovg_matrix_init_identity(&matrix);
|
||||
pluto->clippath = plutovg_rle_create();
|
||||
plutovg_rle_rasterize(pluto->clippath, path, &matrix, &pluto->clip, NULL, plutovg_fill_rule_non_zero);
|
||||
plutovg_path_destroy(path);
|
||||
}
|
||||
|
||||
plutovg_rle_t* rle = state->clippath ? state->clippath : pluto->clippath;
|
||||
plutovg_blend(pluto, rle);
|
||||
}
|
||||
|
||||
void plutovg_fill_preserve(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
plutovg_rle_clear(pluto->rle);
|
||||
plutovg_rle_rasterize(pluto->rle, pluto->path, &state->matrix, &pluto->clip, NULL, state->winding);
|
||||
plutovg_rle_intersect(pluto->rle, state->clippath);
|
||||
plutovg_blend(pluto, pluto->rle);
|
||||
}
|
||||
|
||||
void plutovg_stroke_preserve(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
plutovg_rle_clear(pluto->rle);
|
||||
plutovg_rle_rasterize(pluto->rle, pluto->path, &state->matrix, &pluto->clip, &state->stroke, plutovg_fill_rule_non_zero);
|
||||
plutovg_rle_intersect(pluto->rle, state->clippath);
|
||||
plutovg_blend(pluto, pluto->rle);
|
||||
}
|
||||
|
||||
void plutovg_clip_preserve(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
if(state->clippath)
|
||||
{
|
||||
plutovg_rle_clear(pluto->rle);
|
||||
plutovg_rle_rasterize(pluto->rle, pluto->path, &state->matrix, &pluto->clip, NULL, state->winding);
|
||||
plutovg_rle_intersect(state->clippath, pluto->rle);
|
||||
}
|
||||
else
|
||||
{
|
||||
state->clippath = plutovg_rle_create();
|
||||
plutovg_rle_rasterize(state->clippath, pluto->path, &state->matrix, &pluto->clip, NULL, state->winding);
|
||||
}
|
||||
}
|
||||
|
||||
void plutovg_fill_extents(plutovg_t* pluto, plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
plutovg_rle_clear(pluto->rle);
|
||||
plutovg_rle_rasterize(pluto->rle, pluto->path, &state->matrix, NULL, NULL, state->winding);
|
||||
plutovg_rect_init(rect, pluto->rle->x, pluto->rle->y, pluto->rle->w, pluto->rle->h);
|
||||
}
|
||||
|
||||
void plutovg_stroke_extents(plutovg_t* pluto, plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
plutovg_rle_clear(pluto->rle);
|
||||
plutovg_rle_rasterize(pluto->rle, pluto->path, &state->matrix, NULL, &state->stroke, plutovg_fill_rule_non_zero);
|
||||
plutovg_rect_init(rect, pluto->rle->x, pluto->rle->y, pluto->rle->w, pluto->rle->h);
|
||||
}
|
||||
|
||||
void plutovg_clip_extents(plutovg_t* pluto, plutovg_rect_t* rect)
|
||||
{
|
||||
plutovg_state_t* state = pluto->state;
|
||||
rect->x = state->clippath ? state->clippath->x : pluto->clip.x;
|
||||
rect->y = state->clippath ? state->clippath->y : pluto->clip.y;
|
||||
rect->w = state->clippath ? state->clippath->w : pluto->clip.w;
|
||||
rect->h = state->clippath ? state->clippath->h : pluto->clip.h;
|
||||
}
|
||||
|
||||
void plutovg_reset_clip(plutovg_t* pluto)
|
||||
{
|
||||
plutovg_rle_destroy(pluto->state->clippath);
|
||||
pluto->state->clippath = NULL;
|
||||
}
|
||||
+2090
File diff suppressed because it is too large
Load Diff
+4882
File diff suppressed because it is too large
Load Diff
+461
@@ -0,0 +1,461 @@
|
||||
/***************************************************************************/
|
||||
/* */
|
||||
/* fttrigon.c */
|
||||
/* */
|
||||
/* FreeType trigonometric functions (body). */
|
||||
/* */
|
||||
/* Copyright 2001-2005, 2012-2013 by */
|
||||
/* David Turner, Robert Wilhelm, and Werner Lemberg. */
|
||||
/* */
|
||||
/* This file is part of the FreeType project, and may only be used, */
|
||||
/* modified, and distributed under the terms of the FreeType project */
|
||||
/* license, LICENSE.TXT. By continuing to use, modify, or distribute */
|
||||
/* this file you indicate that you have read the license and */
|
||||
/* understand and accept it fully. */
|
||||
/* */
|
||||
/***************************************************************************/
|
||||
|
||||
#include "sw_ft_math.h"
|
||||
#include <math.h>
|
||||
|
||||
//form https://github.com/chromium/chromium/blob/59afd8336009c9d97c22854c52e0382b62b3aa5e/third_party/abseil-cpp/absl/base/internal/bits.h
|
||||
|
||||
#if defined(_MSC_VER)
|
||||
#include <intrin.h>
|
||||
static unsigned int __inline clz(unsigned int x) {
|
||||
unsigned long r = 0;
|
||||
if (x != 0)
|
||||
{
|
||||
_BitScanReverse(&r, x);
|
||||
}
|
||||
return r;
|
||||
}
|
||||
#define SW_FT_MSB(x) (clz(x))
|
||||
#elif defined(__GNUC__)
|
||||
#define SW_FT_MSB(x) (31 - __builtin_clz(x))
|
||||
#else
|
||||
static unsigned int __inline clz(unsigned int x) {
|
||||
int c = 31;
|
||||
x &= ~x + 1;
|
||||
if (n & 0x0000FFFF) c -= 16;
|
||||
if (n & 0x00FF00FF) c -= 8;
|
||||
if (n & 0x0F0F0F0F) c -= 4;
|
||||
if (n & 0x33333333) c -= 2;
|
||||
if (n & 0x55555555) c -= 1;
|
||||
return c;
|
||||
}
|
||||
#define SW_FT_MSB(x) (clz(x))
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#define SW_FT_PAD_FLOOR(x, n) ((x) & ~((n)-1))
|
||||
#define SW_FT_PAD_ROUND(x, n) SW_FT_PAD_FLOOR((x) + ((n) / 2), n)
|
||||
#define SW_FT_PAD_CEIL(x, n) SW_FT_PAD_FLOOR((x) + ((n)-1), n)
|
||||
|
||||
#define SW_FT_BEGIN_STMNT do {
|
||||
#define SW_FT_END_STMNT \
|
||||
} \
|
||||
while (0)
|
||||
/* transfer sign leaving a positive number */
|
||||
#define SW_FT_MOVE_SIGN(x, s) \
|
||||
SW_FT_BEGIN_STMNT \
|
||||
if (x < 0) { \
|
||||
x = -x; \
|
||||
s = -s; \
|
||||
} \
|
||||
SW_FT_END_STMNT
|
||||
|
||||
SW_FT_Long SW_FT_MulFix(SW_FT_Long a, SW_FT_Long b)
|
||||
{
|
||||
SW_FT_Int s = 1;
|
||||
SW_FT_Long c;
|
||||
|
||||
SW_FT_MOVE_SIGN(a, s);
|
||||
SW_FT_MOVE_SIGN(b, s);
|
||||
|
||||
c = (SW_FT_Long)(((SW_FT_Int64)a * b + 0x8000L) >> 16);
|
||||
|
||||
return (s > 0) ? c : -c;
|
||||
}
|
||||
|
||||
SW_FT_Long SW_FT_MulDiv(SW_FT_Long a, SW_FT_Long b, SW_FT_Long c)
|
||||
{
|
||||
SW_FT_Int s = 1;
|
||||
SW_FT_Long d;
|
||||
|
||||
SW_FT_MOVE_SIGN(a, s);
|
||||
SW_FT_MOVE_SIGN(b, s);
|
||||
SW_FT_MOVE_SIGN(c, s);
|
||||
|
||||
d = (SW_FT_Long)(c > 0 ? ((SW_FT_Int64)a * b + (c >> 1)) / c : 0x7FFFFFFFL);
|
||||
|
||||
return (s > 0) ? d : -d;
|
||||
}
|
||||
|
||||
SW_FT_Long SW_FT_DivFix(SW_FT_Long a, SW_FT_Long b)
|
||||
{
|
||||
SW_FT_Int s = 1;
|
||||
SW_FT_Long q;
|
||||
|
||||
SW_FT_MOVE_SIGN(a, s);
|
||||
SW_FT_MOVE_SIGN(b, s);
|
||||
|
||||
q = (SW_FT_Long)(b > 0 ? (((SW_FT_UInt64)a << 16) + (b >> 1)) / b
|
||||
: 0x7FFFFFFFL);
|
||||
|
||||
return (s < 0 ? -q : q);
|
||||
}
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* This is a fixed-point CORDIC implementation of trigonometric */
|
||||
/* functions as well as transformations between Cartesian and polar */
|
||||
/* coordinates. The angles are represented as 16.16 fixed-point values */
|
||||
/* in degrees, i.e., the angular resolution is 2^-16 degrees. Note that */
|
||||
/* only vectors longer than 2^16*180/pi (or at least 22 bits) on a */
|
||||
/* discrete Cartesian grid can have the same or better angular */
|
||||
/* resolution. Therefore, to maintain this precision, some functions */
|
||||
/* require an interim upscaling of the vectors, whereas others operate */
|
||||
/* with 24-bit long vectors directly. */
|
||||
/* */
|
||||
/*************************************************************************/
|
||||
|
||||
/* the Cordic shrink factor 0.858785336480436 * 2^32 */
|
||||
#define SW_FT_TRIG_SCALE 0xDBD95B16UL
|
||||
|
||||
/* the highest bit in overflow-safe vector components, */
|
||||
/* MSB of 0.858785336480436 * sqrt(0.5) * 2^30 */
|
||||
#define SW_FT_TRIG_SAFE_MSB 29
|
||||
|
||||
/* this table was generated for SW_FT_PI = 180L << 16, i.e. degrees */
|
||||
#define SW_FT_TRIG_MAX_ITERS 23
|
||||
|
||||
static const SW_FT_Fixed ft_trig_arctan_table[] = {
|
||||
1740967L, 919879L, 466945L, 234379L, 117304L, 58666L, 29335L, 14668L,
|
||||
7334L, 3667L, 1833L, 917L, 458L, 229L, 115L, 57L,
|
||||
29L, 14L, 7L, 4L, 2L, 1L};
|
||||
|
||||
/* multiply a given value by the CORDIC shrink factor */
|
||||
static SW_FT_Fixed ft_trig_downscale(SW_FT_Fixed val)
|
||||
{
|
||||
SW_FT_Fixed s;
|
||||
SW_FT_Int64 v;
|
||||
|
||||
s = val;
|
||||
val = SW_FT_ABS(val);
|
||||
|
||||
v = (val * (SW_FT_Int64)SW_FT_TRIG_SCALE) + 0x100000000UL;
|
||||
val = (SW_FT_Fixed)(v >> 32);
|
||||
|
||||
return (s >= 0) ? val : -val;
|
||||
}
|
||||
|
||||
/* undefined and never called for zero vector */
|
||||
static SW_FT_Int ft_trig_prenorm(SW_FT_Vector* vec)
|
||||
{
|
||||
SW_FT_Pos x, y;
|
||||
SW_FT_Int shift;
|
||||
|
||||
x = vec->x;
|
||||
y = vec->y;
|
||||
|
||||
shift = SW_FT_MSB(SW_FT_ABS(x) | SW_FT_ABS(y));
|
||||
|
||||
if (shift <= SW_FT_TRIG_SAFE_MSB) {
|
||||
shift = SW_FT_TRIG_SAFE_MSB - shift;
|
||||
vec->x = (SW_FT_Pos)((SW_FT_ULong)x << shift);
|
||||
vec->y = (SW_FT_Pos)((SW_FT_ULong)y << shift);
|
||||
} else {
|
||||
shift -= SW_FT_TRIG_SAFE_MSB;
|
||||
vec->x = x >> shift;
|
||||
vec->y = y >> shift;
|
||||
shift = -shift;
|
||||
}
|
||||
|
||||
return shift;
|
||||
}
|
||||
|
||||
static void ft_trig_pseudo_rotate(SW_FT_Vector* vec, SW_FT_Angle theta)
|
||||
{
|
||||
SW_FT_Int i;
|
||||
SW_FT_Fixed x, y, xtemp, b;
|
||||
const SW_FT_Fixed* arctanptr;
|
||||
|
||||
x = vec->x;
|
||||
y = vec->y;
|
||||
|
||||
/* Rotate inside [-PI/4,PI/4] sector */
|
||||
while (theta < -SW_FT_ANGLE_PI4) {
|
||||
xtemp = y;
|
||||
y = -x;
|
||||
x = xtemp;
|
||||
theta += SW_FT_ANGLE_PI2;
|
||||
}
|
||||
|
||||
while (theta > SW_FT_ANGLE_PI4) {
|
||||
xtemp = -y;
|
||||
y = x;
|
||||
x = xtemp;
|
||||
theta -= SW_FT_ANGLE_PI2;
|
||||
}
|
||||
|
||||
arctanptr = ft_trig_arctan_table;
|
||||
|
||||
/* Pseudorotations, with right shifts */
|
||||
for (i = 1, b = 1; i < SW_FT_TRIG_MAX_ITERS; b <<= 1, i++) {
|
||||
SW_FT_Fixed v1 = ((y + b) >> i);
|
||||
SW_FT_Fixed v2 = ((x + b) >> i);
|
||||
if (theta < 0) {
|
||||
xtemp = x + v1;
|
||||
y = y - v2;
|
||||
x = xtemp;
|
||||
theta += *arctanptr++;
|
||||
} else {
|
||||
xtemp = x - v1;
|
||||
y = y + v2;
|
||||
x = xtemp;
|
||||
theta -= *arctanptr++;
|
||||
}
|
||||
}
|
||||
|
||||
vec->x = x;
|
||||
vec->y = y;
|
||||
}
|
||||
|
||||
static void ft_trig_pseudo_polarize(SW_FT_Vector* vec)
|
||||
{
|
||||
SW_FT_Angle theta;
|
||||
SW_FT_Int i;
|
||||
SW_FT_Fixed x, y, xtemp, b;
|
||||
const SW_FT_Fixed* arctanptr;
|
||||
|
||||
x = vec->x;
|
||||
y = vec->y;
|
||||
|
||||
/* Get the vector into [-PI/4,PI/4] sector */
|
||||
if (y > x) {
|
||||
if (y > -x) {
|
||||
theta = SW_FT_ANGLE_PI2;
|
||||
xtemp = y;
|
||||
y = -x;
|
||||
x = xtemp;
|
||||
} else {
|
||||
theta = y > 0 ? SW_FT_ANGLE_PI : -SW_FT_ANGLE_PI;
|
||||
x = -x;
|
||||
y = -y;
|
||||
}
|
||||
} else {
|
||||
if (y < -x) {
|
||||
theta = -SW_FT_ANGLE_PI2;
|
||||
xtemp = -y;
|
||||
y = x;
|
||||
x = xtemp;
|
||||
} else {
|
||||
theta = 0;
|
||||
}
|
||||
}
|
||||
|
||||
arctanptr = ft_trig_arctan_table;
|
||||
|
||||
/* Pseudorotations, with right shifts */
|
||||
for (i = 1, b = 1; i < SW_FT_TRIG_MAX_ITERS; b <<= 1, i++) {
|
||||
SW_FT_Fixed v1 = ((y + b) >> i);
|
||||
SW_FT_Fixed v2 = ((x + b) >> i);
|
||||
if (y > 0) {
|
||||
xtemp = x + v1;
|
||||
y = y - v2;
|
||||
x = xtemp;
|
||||
theta += *arctanptr++;
|
||||
} else {
|
||||
xtemp = x - v1;
|
||||
y = y + v2;
|
||||
x = xtemp;
|
||||
theta -= *arctanptr++;
|
||||
}
|
||||
}
|
||||
|
||||
/* round theta */
|
||||
if (theta >= 0)
|
||||
theta = SW_FT_PAD_ROUND(theta, 32);
|
||||
else
|
||||
theta = -SW_FT_PAD_ROUND(-theta, 32);
|
||||
|
||||
vec->x = x;
|
||||
vec->y = theta;
|
||||
}
|
||||
|
||||
/* documentation is in fttrigon.h */
|
||||
|
||||
SW_FT_Fixed SW_FT_Cos(SW_FT_Angle angle)
|
||||
{
|
||||
SW_FT_Vector v;
|
||||
|
||||
v.x = SW_FT_TRIG_SCALE >> 8;
|
||||
v.y = 0;
|
||||
ft_trig_pseudo_rotate(&v, angle);
|
||||
|
||||
return (v.x + 0x80L) >> 8;
|
||||
}
|
||||
|
||||
/* documentation is in fttrigon.h */
|
||||
|
||||
SW_FT_Fixed SW_FT_Sin(SW_FT_Angle angle)
|
||||
{
|
||||
return SW_FT_Cos(SW_FT_ANGLE_PI2 - angle);
|
||||
}
|
||||
|
||||
/* documentation is in fttrigon.h */
|
||||
|
||||
SW_FT_Fixed SW_FT_Tan(SW_FT_Angle angle)
|
||||
{
|
||||
SW_FT_Vector v;
|
||||
|
||||
v.x = SW_FT_TRIG_SCALE >> 8;
|
||||
v.y = 0;
|
||||
ft_trig_pseudo_rotate(&v, angle);
|
||||
|
||||
return SW_FT_DivFix(v.y, v.x);
|
||||
}
|
||||
|
||||
/* documentation is in fttrigon.h */
|
||||
|
||||
SW_FT_Angle SW_FT_Atan2(SW_FT_Fixed dx, SW_FT_Fixed dy)
|
||||
{
|
||||
SW_FT_Vector v;
|
||||
|
||||
if (dx == 0 && dy == 0) return 0;
|
||||
|
||||
v.x = dx;
|
||||
v.y = dy;
|
||||
ft_trig_prenorm(&v);
|
||||
ft_trig_pseudo_polarize(&v);
|
||||
|
||||
return v.y;
|
||||
}
|
||||
|
||||
/* documentation is in fttrigon.h */
|
||||
|
||||
void SW_FT_Vector_Unit(SW_FT_Vector* vec, SW_FT_Angle angle)
|
||||
{
|
||||
vec->x = SW_FT_TRIG_SCALE >> 8;
|
||||
vec->y = 0;
|
||||
ft_trig_pseudo_rotate(vec, angle);
|
||||
vec->x = (vec->x + 0x80L) >> 8;
|
||||
vec->y = (vec->y + 0x80L) >> 8;
|
||||
}
|
||||
|
||||
/* these macros return 0 for positive numbers,
|
||||
and -1 for negative ones */
|
||||
#define SW_FT_SIGN_LONG(x) ((x) >> (SW_FT_SIZEOF_LONG * 8 - 1))
|
||||
#define SW_FT_SIGN_INT(x) ((x) >> (SW_FT_SIZEOF_INT * 8 - 1))
|
||||
#define SW_FT_SIGN_INT32(x) ((x) >> 31)
|
||||
#define SW_FT_SIGN_INT16(x) ((x) >> 15)
|
||||
|
||||
/* documentation is in fttrigon.h */
|
||||
|
||||
void SW_FT_Vector_Rotate(SW_FT_Vector* vec, SW_FT_Angle angle)
|
||||
{
|
||||
SW_FT_Int shift;
|
||||
SW_FT_Vector v;
|
||||
|
||||
v.x = vec->x;
|
||||
v.y = vec->y;
|
||||
|
||||
if (angle && (v.x != 0 || v.y != 0)) {
|
||||
shift = ft_trig_prenorm(&v);
|
||||
ft_trig_pseudo_rotate(&v, angle);
|
||||
v.x = ft_trig_downscale(v.x);
|
||||
v.y = ft_trig_downscale(v.y);
|
||||
|
||||
if (shift > 0) {
|
||||
SW_FT_Int32 half = (SW_FT_Int32)1L << (shift - 1);
|
||||
|
||||
vec->x = (v.x + half + SW_FT_SIGN_LONG(v.x)) >> shift;
|
||||
vec->y = (v.y + half + SW_FT_SIGN_LONG(v.y)) >> shift;
|
||||
} else {
|
||||
shift = -shift;
|
||||
vec->x = (SW_FT_Pos)((SW_FT_ULong)v.x << shift);
|
||||
vec->y = (SW_FT_Pos)((SW_FT_ULong)v.y << shift);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* documentation is in fttrigon.h */
|
||||
|
||||
SW_FT_Fixed SW_FT_Vector_Length(SW_FT_Vector* vec)
|
||||
{
|
||||
SW_FT_Int shift;
|
||||
SW_FT_Vector v;
|
||||
|
||||
v = *vec;
|
||||
|
||||
/* handle trivial cases */
|
||||
if (v.x == 0) {
|
||||
return SW_FT_ABS(v.y);
|
||||
} else if (v.y == 0) {
|
||||
return SW_FT_ABS(v.x);
|
||||
}
|
||||
|
||||
/* general case */
|
||||
shift = ft_trig_prenorm(&v);
|
||||
ft_trig_pseudo_polarize(&v);
|
||||
|
||||
v.x = ft_trig_downscale(v.x);
|
||||
|
||||
if (shift > 0) return (v.x + (1 << (shift - 1))) >> shift;
|
||||
|
||||
return (SW_FT_Fixed)((SW_FT_UInt32)v.x << -shift);
|
||||
}
|
||||
|
||||
/* documentation is in fttrigon.h */
|
||||
|
||||
void SW_FT_Vector_Polarize(SW_FT_Vector* vec, SW_FT_Fixed* length,
|
||||
SW_FT_Angle* angle)
|
||||
{
|
||||
SW_FT_Int shift;
|
||||
SW_FT_Vector v;
|
||||
|
||||
v = *vec;
|
||||
|
||||
if (v.x == 0 && v.y == 0) return;
|
||||
|
||||
shift = ft_trig_prenorm(&v);
|
||||
ft_trig_pseudo_polarize(&v);
|
||||
|
||||
v.x = ft_trig_downscale(v.x);
|
||||
|
||||
*length = (shift >= 0) ? (v.x >> shift)
|
||||
: (SW_FT_Fixed)((SW_FT_UInt32)v.x << -shift);
|
||||
*angle = v.y;
|
||||
}
|
||||
|
||||
/* documentation is in fttrigon.h */
|
||||
|
||||
void SW_FT_Vector_From_Polar(SW_FT_Vector* vec, SW_FT_Fixed length,
|
||||
SW_FT_Angle angle)
|
||||
{
|
||||
vec->x = length;
|
||||
vec->y = 0;
|
||||
|
||||
SW_FT_Vector_Rotate(vec, angle);
|
||||
}
|
||||
|
||||
/* documentation is in fttrigon.h */
|
||||
|
||||
SW_FT_Angle SW_FT_Angle_Diff( SW_FT_Angle angle1, SW_FT_Angle angle2 )
|
||||
{
|
||||
SW_FT_Angle delta = angle2 - angle1;
|
||||
|
||||
while ( delta <= -SW_FT_ANGLE_PI )
|
||||
delta += SW_FT_ANGLE_2PI;
|
||||
|
||||
while ( delta > SW_FT_ANGLE_PI )
|
||||
delta -= SW_FT_ANGLE_2PI;
|
||||
|
||||
return delta;
|
||||
}
|
||||
|
||||
/* END */
|
||||
+438
@@ -0,0 +1,438 @@
|
||||
#ifndef SW_FT_MATH_H
|
||||
#define SW_FT_MATH_H
|
||||
|
||||
/***************************************************************************/
|
||||
/* */
|
||||
/* fttrigon.h */
|
||||
/* */
|
||||
/* FreeType trigonometric functions (specification). */
|
||||
/* */
|
||||
/* Copyright 2001, 2003, 2005, 2007, 2013 by */
|
||||
/* David Turner, Robert Wilhelm, and Werner Lemberg. */
|
||||
/* */
|
||||
/* This file is part of the FreeType project, and may only be used, */
|
||||
/* modified, and distributed under the terms of the FreeType project */
|
||||
/* license, LICENSE.TXT. By continuing to use, modify, or distribute */
|
||||
/* this file you indicate that you have read the license and */
|
||||
/* understand and accept it fully. */
|
||||
/* */
|
||||
/***************************************************************************/
|
||||
|
||||
#include "sw_ft_types.h"
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* The min and max functions missing in C. As usual, be careful not to */
|
||||
/* write things like SW_FT_MIN( a++, b++ ) to avoid side effects. */
|
||||
/* */
|
||||
#define SW_FT_MIN( a, b ) ( (a) < (b) ? (a) : (b) )
|
||||
#define SW_FT_MAX( a, b ) ( (a) > (b) ? (a) : (b) )
|
||||
|
||||
#define SW_FT_ABS( a ) ( (a) < 0 ? -(a) : (a) )
|
||||
|
||||
/*
|
||||
* Approximate sqrt(x*x+y*y) using the `alpha max plus beta min'
|
||||
* algorithm. We use alpha = 1, beta = 3/8, giving us results with a
|
||||
* largest error less than 7% compared to the exact value.
|
||||
*/
|
||||
#define SW_FT_HYPOT( x, y ) \
|
||||
( x = SW_FT_ABS( x ), \
|
||||
y = SW_FT_ABS( y ), \
|
||||
x > y ? x + ( 3 * y >> 3 ) \
|
||||
: y + ( 3 * x >> 3 ) )
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Function> */
|
||||
/* SW_FT_MulFix */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A very simple function used to perform the computation */
|
||||
/* `(a*b)/0x10000' with maximum accuracy. Most of the time this is */
|
||||
/* used to multiply a given value by a 16.16 fixed-point factor. */
|
||||
/* */
|
||||
/* <Input> */
|
||||
/* a :: The first multiplier. */
|
||||
/* b :: The second multiplier. Use a 16.16 factor here whenever */
|
||||
/* possible (see note below). */
|
||||
/* */
|
||||
/* <Return> */
|
||||
/* The result of `(a*b)/0x10000'. */
|
||||
/* */
|
||||
/* <Note> */
|
||||
/* This function has been optimized for the case where the absolute */
|
||||
/* value of `a' is less than 2048, and `b' is a 16.16 scaling factor. */
|
||||
/* As this happens mainly when scaling from notional units to */
|
||||
/* fractional pixels in FreeType, it resulted in noticeable speed */
|
||||
/* improvements between versions 2.x and 1.x. */
|
||||
/* */
|
||||
/* As a conclusion, always try to place a 16.16 factor as the */
|
||||
/* _second_ argument of this function; this can make a great */
|
||||
/* difference. */
|
||||
/* */
|
||||
SW_FT_Long
|
||||
SW_FT_MulFix( SW_FT_Long a,
|
||||
SW_FT_Long b );
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Function> */
|
||||
/* SW_FT_MulDiv */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A very simple function used to perform the computation `(a*b)/c' */
|
||||
/* with maximum accuracy (it uses a 64-bit intermediate integer */
|
||||
/* whenever necessary). */
|
||||
/* */
|
||||
/* This function isn't necessarily as fast as some processor specific */
|
||||
/* operations, but is at least completely portable. */
|
||||
/* */
|
||||
/* <Input> */
|
||||
/* a :: The first multiplier. */
|
||||
/* b :: The second multiplier. */
|
||||
/* c :: The divisor. */
|
||||
/* */
|
||||
/* <Return> */
|
||||
/* The result of `(a*b)/c'. This function never traps when trying to */
|
||||
/* divide by zero; it simply returns `MaxInt' or `MinInt' depending */
|
||||
/* on the signs of `a' and `b'. */
|
||||
/* */
|
||||
SW_FT_Long
|
||||
SW_FT_MulDiv( SW_FT_Long a,
|
||||
SW_FT_Long b,
|
||||
SW_FT_Long c );
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Function> */
|
||||
/* SW_FT_DivFix */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A very simple function used to perform the computation */
|
||||
/* `(a*0x10000)/b' with maximum accuracy. Most of the time, this is */
|
||||
/* used to divide a given value by a 16.16 fixed-point factor. */
|
||||
/* */
|
||||
/* <Input> */
|
||||
/* a :: The numerator. */
|
||||
/* b :: The denominator. Use a 16.16 factor here. */
|
||||
/* */
|
||||
/* <Return> */
|
||||
/* The result of `(a*0x10000)/b'. */
|
||||
/* */
|
||||
SW_FT_Long
|
||||
SW_FT_DivFix( SW_FT_Long a,
|
||||
SW_FT_Long b );
|
||||
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Section> */
|
||||
/* computations */
|
||||
/* */
|
||||
/*************************************************************************/
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @type:
|
||||
* SW_FT_Angle
|
||||
*
|
||||
* @description:
|
||||
* This type is used to model angle values in FreeType. Note that the
|
||||
* angle is a 16.16 fixed-point value expressed in degrees.
|
||||
*
|
||||
*/
|
||||
typedef SW_FT_Fixed SW_FT_Angle;
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @macro:
|
||||
* SW_FT_ANGLE_PI
|
||||
*
|
||||
* @description:
|
||||
* The angle pi expressed in @SW_FT_Angle units.
|
||||
*
|
||||
*/
|
||||
#define SW_FT_ANGLE_PI ( 180L << 16 )
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @macro:
|
||||
* SW_FT_ANGLE_2PI
|
||||
*
|
||||
* @description:
|
||||
* The angle 2*pi expressed in @SW_FT_Angle units.
|
||||
*
|
||||
*/
|
||||
#define SW_FT_ANGLE_2PI ( SW_FT_ANGLE_PI * 2 )
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @macro:
|
||||
* SW_FT_ANGLE_PI2
|
||||
*
|
||||
* @description:
|
||||
* The angle pi/2 expressed in @SW_FT_Angle units.
|
||||
*
|
||||
*/
|
||||
#define SW_FT_ANGLE_PI2 ( SW_FT_ANGLE_PI / 2 )
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @macro:
|
||||
* SW_FT_ANGLE_PI4
|
||||
*
|
||||
* @description:
|
||||
* The angle pi/4 expressed in @SW_FT_Angle units.
|
||||
*
|
||||
*/
|
||||
#define SW_FT_ANGLE_PI4 ( SW_FT_ANGLE_PI / 4 )
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Sin
|
||||
*
|
||||
* @description:
|
||||
* Return the sinus of a given angle in fixed-point format.
|
||||
*
|
||||
* @input:
|
||||
* angle ::
|
||||
* The input angle.
|
||||
*
|
||||
* @return:
|
||||
* The sinus value.
|
||||
*
|
||||
* @note:
|
||||
* If you need both the sinus and cosinus for a given angle, use the
|
||||
* function @SW_FT_Vector_Unit.
|
||||
*
|
||||
*/
|
||||
SW_FT_Fixed
|
||||
SW_FT_Sin( SW_FT_Angle angle );
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Cos
|
||||
*
|
||||
* @description:
|
||||
* Return the cosinus of a given angle in fixed-point format.
|
||||
*
|
||||
* @input:
|
||||
* angle ::
|
||||
* The input angle.
|
||||
*
|
||||
* @return:
|
||||
* The cosinus value.
|
||||
*
|
||||
* @note:
|
||||
* If you need both the sinus and cosinus for a given angle, use the
|
||||
* function @SW_FT_Vector_Unit.
|
||||
*
|
||||
*/
|
||||
SW_FT_Fixed
|
||||
SW_FT_Cos( SW_FT_Angle angle );
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Tan
|
||||
*
|
||||
* @description:
|
||||
* Return the tangent of a given angle in fixed-point format.
|
||||
*
|
||||
* @input:
|
||||
* angle ::
|
||||
* The input angle.
|
||||
*
|
||||
* @return:
|
||||
* The tangent value.
|
||||
*
|
||||
*/
|
||||
SW_FT_Fixed
|
||||
SW_FT_Tan( SW_FT_Angle angle );
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Atan2
|
||||
*
|
||||
* @description:
|
||||
* Return the arc-tangent corresponding to a given vector (x,y) in
|
||||
* the 2d plane.
|
||||
*
|
||||
* @input:
|
||||
* x ::
|
||||
* The horizontal vector coordinate.
|
||||
*
|
||||
* y ::
|
||||
* The vertical vector coordinate.
|
||||
*
|
||||
* @return:
|
||||
* The arc-tangent value (i.e. angle).
|
||||
*
|
||||
*/
|
||||
SW_FT_Angle
|
||||
SW_FT_Atan2( SW_FT_Fixed x,
|
||||
SW_FT_Fixed y );
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Angle_Diff
|
||||
*
|
||||
* @description:
|
||||
* Return the difference between two angles. The result is always
|
||||
* constrained to the ]-PI..PI] interval.
|
||||
*
|
||||
* @input:
|
||||
* angle1 ::
|
||||
* First angle.
|
||||
*
|
||||
* angle2 ::
|
||||
* Second angle.
|
||||
*
|
||||
* @return:
|
||||
* Constrained value of `value2-value1'.
|
||||
*
|
||||
*/
|
||||
SW_FT_Angle
|
||||
SW_FT_Angle_Diff( SW_FT_Angle angle1,
|
||||
SW_FT_Angle angle2 );
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Vector_Unit
|
||||
*
|
||||
* @description:
|
||||
* Return the unit vector corresponding to a given angle. After the
|
||||
* call, the value of `vec.x' will be `sin(angle)', and the value of
|
||||
* `vec.y' will be `cos(angle)'.
|
||||
*
|
||||
* This function is useful to retrieve both the sinus and cosinus of a
|
||||
* given angle quickly.
|
||||
*
|
||||
* @output:
|
||||
* vec ::
|
||||
* The address of target vector.
|
||||
*
|
||||
* @input:
|
||||
* angle ::
|
||||
* The input angle.
|
||||
*
|
||||
*/
|
||||
void
|
||||
SW_FT_Vector_Unit( SW_FT_Vector* vec,
|
||||
SW_FT_Angle angle );
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Vector_Rotate
|
||||
*
|
||||
* @description:
|
||||
* Rotate a vector by a given angle.
|
||||
*
|
||||
* @inout:
|
||||
* vec ::
|
||||
* The address of target vector.
|
||||
*
|
||||
* @input:
|
||||
* angle ::
|
||||
* The input angle.
|
||||
*
|
||||
*/
|
||||
void
|
||||
SW_FT_Vector_Rotate( SW_FT_Vector* vec,
|
||||
SW_FT_Angle angle );
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Vector_Length
|
||||
*
|
||||
* @description:
|
||||
* Return the length of a given vector.
|
||||
*
|
||||
* @input:
|
||||
* vec ::
|
||||
* The address of target vector.
|
||||
*
|
||||
* @return:
|
||||
* The vector length, expressed in the same units that the original
|
||||
* vector coordinates.
|
||||
*
|
||||
*/
|
||||
SW_FT_Fixed
|
||||
SW_FT_Vector_Length( SW_FT_Vector* vec );
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Vector_Polarize
|
||||
*
|
||||
* @description:
|
||||
* Compute both the length and angle of a given vector.
|
||||
*
|
||||
* @input:
|
||||
* vec ::
|
||||
* The address of source vector.
|
||||
*
|
||||
* @output:
|
||||
* length ::
|
||||
* The vector length.
|
||||
*
|
||||
* angle ::
|
||||
* The vector angle.
|
||||
*
|
||||
*/
|
||||
void
|
||||
SW_FT_Vector_Polarize( SW_FT_Vector* vec,
|
||||
SW_FT_Fixed *length,
|
||||
SW_FT_Angle *angle );
|
||||
|
||||
|
||||
/*************************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Vector_From_Polar
|
||||
*
|
||||
* @description:
|
||||
* Compute vector coordinates from a length and angle.
|
||||
*
|
||||
* @output:
|
||||
* vec ::
|
||||
* The address of source vector.
|
||||
*
|
||||
* @input:
|
||||
* length ::
|
||||
* The vector length.
|
||||
*
|
||||
* angle ::
|
||||
* The vector angle.
|
||||
*
|
||||
*/
|
||||
void
|
||||
SW_FT_Vector_From_Polar( SW_FT_Vector* vec,
|
||||
SW_FT_Fixed length,
|
||||
SW_FT_Angle angle );
|
||||
|
||||
|
||||
#endif // SW_FT_MATH_H
|
||||
+1423
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,607 @@
|
||||
#ifndef SW_FT_IMG_H
|
||||
#define SW_FT_IMG_H
|
||||
/***************************************************************************/
|
||||
/* */
|
||||
/* ftimage.h */
|
||||
/* */
|
||||
/* FreeType glyph image formats and default raster interface */
|
||||
/* (specification). */
|
||||
/* */
|
||||
/* Copyright 1996-2010, 2013 by */
|
||||
/* David Turner, Robert Wilhelm, and Werner Lemberg. */
|
||||
/* */
|
||||
/* This file is part of the FreeType project, and may only be used, */
|
||||
/* modified, and distributed under the terms of the FreeType project */
|
||||
/* license, LICENSE.TXT. By continuing to use, modify, or distribute */
|
||||
/* this file you indicate that you have read the license and */
|
||||
/* understand and accept it fully. */
|
||||
/* */
|
||||
/***************************************************************************/
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* Note: A `raster' is simply a scan-line converter, used to render */
|
||||
/* SW_FT_Outlines into SW_FT_Bitmaps. */
|
||||
/* */
|
||||
/*************************************************************************/
|
||||
|
||||
#include "sw_ft_types.h"
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Struct> */
|
||||
/* FT_BBox */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A structure used to hold an outline's bounding box, i.e., the */
|
||||
/* coordinates of its extrema in the horizontal and vertical */
|
||||
/* directions. */
|
||||
/* */
|
||||
/* <Fields> */
|
||||
/* xMin :: The horizontal minimum (left-most). */
|
||||
/* */
|
||||
/* yMin :: The vertical minimum (bottom-most). */
|
||||
/* */
|
||||
/* xMax :: The horizontal maximum (right-most). */
|
||||
/* */
|
||||
/* yMax :: The vertical maximum (top-most). */
|
||||
/* */
|
||||
/* <Note> */
|
||||
/* The bounding box is specified with the coordinates of the lower */
|
||||
/* left and the upper right corner. In PostScript, those values are */
|
||||
/* often called (llx,lly) and (urx,ury), respectively. */
|
||||
/* */
|
||||
/* If `yMin' is negative, this value gives the glyph's descender. */
|
||||
/* Otherwise, the glyph doesn't descend below the baseline. */
|
||||
/* Similarly, if `ymax' is positive, this value gives the glyph's */
|
||||
/* ascender. */
|
||||
/* */
|
||||
/* `xMin' gives the horizontal distance from the glyph's origin to */
|
||||
/* the left edge of the glyph's bounding box. If `xMin' is negative, */
|
||||
/* the glyph extends to the left of the origin. */
|
||||
/* */
|
||||
typedef struct SW_FT_BBox_
|
||||
{
|
||||
SW_FT_Pos xMin, yMin;
|
||||
SW_FT_Pos xMax, yMax;
|
||||
|
||||
} SW_FT_BBox;
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Struct> */
|
||||
/* SW_FT_Outline */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* This structure is used to describe an outline to the scan-line */
|
||||
/* converter. */
|
||||
/* */
|
||||
/* <Fields> */
|
||||
/* n_contours :: The number of contours in the outline. */
|
||||
/* */
|
||||
/* n_points :: The number of points in the outline. */
|
||||
/* */
|
||||
/* points :: A pointer to an array of `n_points' @SW_FT_Vector */
|
||||
/* elements, giving the outline's point coordinates. */
|
||||
/* */
|
||||
/* tags :: A pointer to an array of `n_points' chars, giving */
|
||||
/* each outline point's type. */
|
||||
/* */
|
||||
/* If bit~0 is unset, the point is `off' the curve, */
|
||||
/* i.e., a Bézier control point, while it is `on' if */
|
||||
/* set. */
|
||||
/* */
|
||||
/* Bit~1 is meaningful for `off' points only. If set, */
|
||||
/* it indicates a third-order Bézier arc control point; */
|
||||
/* and a second-order control point if unset. */
|
||||
/* */
|
||||
/* If bit~2 is set, bits 5-7 contain the drop-out mode */
|
||||
/* (as defined in the OpenType specification; the value */
|
||||
/* is the same as the argument to the SCANMODE */
|
||||
/* instruction). */
|
||||
/* */
|
||||
/* Bits 3 and~4 are reserved for internal purposes. */
|
||||
/* */
|
||||
/* contours :: An array of `n_contours' shorts, giving the end */
|
||||
/* point of each contour within the outline. For */
|
||||
/* example, the first contour is defined by the points */
|
||||
/* `0' to `contours[0]', the second one is defined by */
|
||||
/* the points `contours[0]+1' to `contours[1]', etc. */
|
||||
/* */
|
||||
/* flags :: A set of bit flags used to characterize the outline */
|
||||
/* and give hints to the scan-converter and hinter on */
|
||||
/* how to convert/grid-fit it. See @SW_FT_OUTLINE_FLAGS.*/
|
||||
/* */
|
||||
typedef struct SW_FT_Outline_
|
||||
{
|
||||
short n_contours; /* number of contours in glyph */
|
||||
short n_points; /* number of points in the glyph */
|
||||
|
||||
SW_FT_Vector* points; /* the outline's points */
|
||||
char* tags; /* the points flags */
|
||||
short* contours; /* the contour end points */
|
||||
char* contours_flag; /* the contour open flags */
|
||||
|
||||
int flags; /* outline masks */
|
||||
|
||||
} SW_FT_Outline;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Enum> */
|
||||
/* SW_FT_OUTLINE_FLAGS */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A list of bit-field constants use for the flags in an outline's */
|
||||
/* `flags' field. */
|
||||
/* */
|
||||
/* <Values> */
|
||||
/* SW_FT_OUTLINE_NONE :: */
|
||||
/* Value~0 is reserved. */
|
||||
/* */
|
||||
/* SW_FT_OUTLINE_OWNER :: */
|
||||
/* If set, this flag indicates that the outline's field arrays */
|
||||
/* (i.e., `points', `flags', and `contours') are `owned' by the */
|
||||
/* outline object, and should thus be freed when it is destroyed. */
|
||||
/* */
|
||||
/* SW_FT_OUTLINE_EVEN_ODD_FILL :: */
|
||||
/* By default, outlines are filled using the non-zero winding rule. */
|
||||
/* If set to 1, the outline will be filled using the even-odd fill */
|
||||
/* rule (only works with the smooth rasterizer). */
|
||||
/* */
|
||||
/* SW_FT_OUTLINE_REVERSE_FILL :: */
|
||||
/* By default, outside contours of an outline are oriented in */
|
||||
/* clock-wise direction, as defined in the TrueType specification. */
|
||||
/* This flag is set if the outline uses the opposite direction */
|
||||
/* (typically for Type~1 fonts). This flag is ignored by the scan */
|
||||
/* converter. */
|
||||
/* */
|
||||
/* */
|
||||
/* */
|
||||
/* There exists a second mechanism to pass the drop-out mode to the */
|
||||
/* B/W rasterizer; see the `tags' field in @SW_FT_Outline. */
|
||||
/* */
|
||||
/* Please refer to the description of the `SCANTYPE' instruction in */
|
||||
/* the OpenType specification (in file `ttinst1.doc') how simple */
|
||||
/* drop-outs, smart drop-outs, and stubs are defined. */
|
||||
/* */
|
||||
#define SW_FT_OUTLINE_NONE 0x0
|
||||
#define SW_FT_OUTLINE_OWNER 0x1
|
||||
#define SW_FT_OUTLINE_EVEN_ODD_FILL 0x2
|
||||
#define SW_FT_OUTLINE_REVERSE_FILL 0x4
|
||||
|
||||
/* */
|
||||
|
||||
#define SW_FT_CURVE_TAG( flag ) ( flag & 3 )
|
||||
|
||||
#define SW_FT_CURVE_TAG_ON 1
|
||||
#define SW_FT_CURVE_TAG_CONIC 0
|
||||
#define SW_FT_CURVE_TAG_CUBIC 2
|
||||
|
||||
|
||||
#define SW_FT_Curve_Tag_On SW_FT_CURVE_TAG_ON
|
||||
#define SW_FT_Curve_Tag_Conic SW_FT_CURVE_TAG_CONIC
|
||||
#define SW_FT_Curve_Tag_Cubic SW_FT_CURVE_TAG_CUBIC
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* A raster is a scan converter, in charge of rendering an outline into */
|
||||
/* a a bitmap. This section contains the public API for rasters. */
|
||||
/* */
|
||||
/* Note that in FreeType 2, all rasters are now encapsulated within */
|
||||
/* specific modules called `renderers'. See `ftrender.h' for more */
|
||||
/* details on renderers. */
|
||||
/* */
|
||||
/*************************************************************************/
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_Raster */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A handle (pointer) to a raster object. Each object can be used */
|
||||
/* independently to convert an outline into a bitmap or pixmap. */
|
||||
/* */
|
||||
typedef struct SW_FT_RasterRec_* SW_FT_Raster;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Struct> */
|
||||
/* SW_FT_Span */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A structure used to model a single span of gray (or black) pixels */
|
||||
/* when rendering a monochrome or anti-aliased bitmap. */
|
||||
/* */
|
||||
/* <Fields> */
|
||||
/* x :: The span's horizontal start position. */
|
||||
/* */
|
||||
/* len :: The span's length in pixels. */
|
||||
/* */
|
||||
/* coverage :: The span color/coverage, ranging from 0 (background) */
|
||||
/* to 255 (foreground). Only used for anti-aliased */
|
||||
/* rendering. */
|
||||
/* */
|
||||
/* <Note> */
|
||||
/* This structure is used by the span drawing callback type named */
|
||||
/* @SW_FT_SpanFunc that takes the y~coordinate of the span as a */
|
||||
/* parameter. */
|
||||
/* */
|
||||
/* The coverage value is always between 0 and 255. If you want less */
|
||||
/* gray values, the callback function has to reduce them. */
|
||||
/* */
|
||||
typedef struct SW_FT_Span_
|
||||
{
|
||||
short x;
|
||||
short y;
|
||||
unsigned short len;
|
||||
unsigned char coverage;
|
||||
|
||||
} SW_FT_Span;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <FuncType> */
|
||||
/* SW_FT_SpanFunc */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A function used as a call-back by the anti-aliased renderer in */
|
||||
/* order to let client applications draw themselves the gray pixel */
|
||||
/* spans on each scan line. */
|
||||
/* */
|
||||
/* <Input> */
|
||||
/* y :: The scanline's y~coordinate. */
|
||||
/* */
|
||||
/* count :: The number of spans to draw on this scanline. */
|
||||
/* */
|
||||
/* spans :: A table of `count' spans to draw on the scanline. */
|
||||
/* */
|
||||
/* user :: User-supplied data that is passed to the callback. */
|
||||
/* */
|
||||
/* <Note> */
|
||||
/* This callback allows client applications to directly render the */
|
||||
/* gray spans of the anti-aliased bitmap to any kind of surfaces. */
|
||||
/* */
|
||||
/* This can be used to write anti-aliased outlines directly to a */
|
||||
/* given background bitmap, and even perform translucency. */
|
||||
/* */
|
||||
/* Note that the `count' field cannot be greater than a fixed value */
|
||||
/* defined by the `SW_FT_MAX_GRAY_SPANS' configuration macro in */
|
||||
/* `ftoption.h'. By default, this value is set to~32, which means */
|
||||
/* that if there are more than 32~spans on a given scanline, the */
|
||||
/* callback is called several times with the same `y' parameter in */
|
||||
/* order to draw all callbacks. */
|
||||
/* */
|
||||
/* Otherwise, the callback is only called once per scan-line, and */
|
||||
/* only for those scanlines that do have `gray' pixels on them. */
|
||||
/* */
|
||||
typedef void
|
||||
(*SW_FT_SpanFunc)( int count,
|
||||
const SW_FT_Span* spans,
|
||||
void* user );
|
||||
|
||||
typedef void
|
||||
(*SW_FT_BboxFunc)( int x, int y, int w, int h,
|
||||
void* user);
|
||||
|
||||
#define SW_FT_Raster_Span_Func SW_FT_SpanFunc
|
||||
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Enum> */
|
||||
/* SW_FT_RASTER_FLAG_XXX */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A list of bit flag constants as used in the `flags' field of a */
|
||||
/* @SW_FT_Raster_Params structure. */
|
||||
/* */
|
||||
/* <Values> */
|
||||
/* SW_FT_RASTER_FLAG_DEFAULT :: This value is 0. */
|
||||
/* */
|
||||
/* SW_FT_RASTER_FLAG_AA :: This flag is set to indicate that an */
|
||||
/* anti-aliased glyph image should be */
|
||||
/* generated. Otherwise, it will be */
|
||||
/* monochrome (1-bit). */
|
||||
/* */
|
||||
/* SW_FT_RASTER_FLAG_DIRECT :: This flag is set to indicate direct */
|
||||
/* rendering. In this mode, client */
|
||||
/* applications must provide their own span */
|
||||
/* callback. This lets them directly */
|
||||
/* draw or compose over an existing bitmap. */
|
||||
/* If this bit is not set, the target */
|
||||
/* pixmap's buffer _must_ be zeroed before */
|
||||
/* rendering. */
|
||||
/* */
|
||||
/* Note that for now, direct rendering is */
|
||||
/* only possible with anti-aliased glyphs. */
|
||||
/* */
|
||||
/* SW_FT_RASTER_FLAG_CLIP :: This flag is only used in direct */
|
||||
/* rendering mode. If set, the output will */
|
||||
/* be clipped to a box specified in the */
|
||||
/* `clip_box' field of the */
|
||||
/* @SW_FT_Raster_Params structure. */
|
||||
/* */
|
||||
/* Note that by default, the glyph bitmap */
|
||||
/* is clipped to the target pixmap, except */
|
||||
/* in direct rendering mode where all spans */
|
||||
/* are generated if no clipping box is set. */
|
||||
/* */
|
||||
#define SW_FT_RASTER_FLAG_DEFAULT 0x0
|
||||
#define SW_FT_RASTER_FLAG_AA 0x1
|
||||
#define SW_FT_RASTER_FLAG_DIRECT 0x2
|
||||
#define SW_FT_RASTER_FLAG_CLIP 0x4
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Struct> */
|
||||
/* SW_FT_Raster_Params */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A structure to hold the arguments used by a raster's render */
|
||||
/* function. */
|
||||
/* */
|
||||
/* <Fields> */
|
||||
/* target :: The target bitmap. */
|
||||
/* */
|
||||
/* source :: A pointer to the source glyph image (e.g., an */
|
||||
/* @SW_FT_Outline). */
|
||||
/* */
|
||||
/* flags :: The rendering flags. */
|
||||
/* */
|
||||
/* gray_spans :: The gray span drawing callback. */
|
||||
/* */
|
||||
/* black_spans :: The black span drawing callback. UNIMPLEMENTED! */
|
||||
/* */
|
||||
/* bit_test :: The bit test callback. UNIMPLEMENTED! */
|
||||
/* */
|
||||
/* bit_set :: The bit set callback. UNIMPLEMENTED! */
|
||||
/* */
|
||||
/* user :: User-supplied data that is passed to each drawing */
|
||||
/* callback. */
|
||||
/* */
|
||||
/* clip_box :: An optional clipping box. It is only used in */
|
||||
/* direct rendering mode. Note that coordinates here */
|
||||
/* should be expressed in _integer_ pixels (and not in */
|
||||
/* 26.6 fixed-point units). */
|
||||
/* */
|
||||
/* <Note> */
|
||||
/* An anti-aliased glyph bitmap is drawn if the @SW_FT_RASTER_FLAG_AA */
|
||||
/* bit flag is set in the `flags' field, otherwise a monochrome */
|
||||
/* bitmap is generated. */
|
||||
/* */
|
||||
/* If the @SW_FT_RASTER_FLAG_DIRECT bit flag is set in `flags', the */
|
||||
/* raster will call the `gray_spans' callback to draw gray pixel */
|
||||
/* spans, in the case of an aa glyph bitmap, it will call */
|
||||
/* `black_spans', and `bit_test' and `bit_set' in the case of a */
|
||||
/* monochrome bitmap. This allows direct composition over a */
|
||||
/* pre-existing bitmap through user-provided callbacks to perform the */
|
||||
/* span drawing/composition. */
|
||||
/* */
|
||||
/* Note that the `bit_test' and `bit_set' callbacks are required when */
|
||||
/* rendering a monochrome bitmap, as they are crucial to implement */
|
||||
/* correct drop-out control as defined in the TrueType specification. */
|
||||
/* */
|
||||
typedef struct SW_FT_Raster_Params_
|
||||
{
|
||||
const void* source;
|
||||
int flags;
|
||||
SW_FT_SpanFunc gray_spans;
|
||||
SW_FT_BboxFunc bbox_cb;
|
||||
void* user;
|
||||
SW_FT_BBox clip_box;
|
||||
|
||||
} SW_FT_Raster_Params;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Function> */
|
||||
/* SW_FT_Outline_Check */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* Check the contents of an outline descriptor. */
|
||||
/* */
|
||||
/* <Input> */
|
||||
/* outline :: A handle to a source outline. */
|
||||
/* */
|
||||
/* <Return> */
|
||||
/* FreeType error code. 0~means success. */
|
||||
/* */
|
||||
SW_FT_Error
|
||||
SW_FT_Outline_Check( SW_FT_Outline* outline );
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Function> */
|
||||
/* SW_FT_Outline_Get_CBox */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* Return an outline's `control box'. The control box encloses all */
|
||||
/* the outline's points, including Bézier control points. Though it */
|
||||
/* coincides with the exact bounding box for most glyphs, it can be */
|
||||
/* slightly larger in some situations (like when rotating an outline */
|
||||
/* that contains Bézier outside arcs). */
|
||||
/* */
|
||||
/* Computing the control box is very fast, while getting the bounding */
|
||||
/* box can take much more time as it needs to walk over all segments */
|
||||
/* and arcs in the outline. To get the latter, you can use the */
|
||||
/* `ftbbox' component, which is dedicated to this single task. */
|
||||
/* */
|
||||
/* <Input> */
|
||||
/* outline :: A pointer to the source outline descriptor. */
|
||||
/* */
|
||||
/* <Output> */
|
||||
/* acbox :: The outline's control box. */
|
||||
/* */
|
||||
/* <Note> */
|
||||
/* See @SW_FT_Glyph_Get_CBox for a discussion of tricky fonts. */
|
||||
/* */
|
||||
void
|
||||
SW_FT_Outline_Get_CBox( const SW_FT_Outline* outline,
|
||||
SW_FT_BBox *acbox );
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <FuncType> */
|
||||
/* SW_FT_Raster_NewFunc */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A function used to create a new raster object. */
|
||||
/* */
|
||||
/* <Input> */
|
||||
/* memory :: A handle to the memory allocator. */
|
||||
/* */
|
||||
/* <Output> */
|
||||
/* raster :: A handle to the new raster object. */
|
||||
/* */
|
||||
/* <Return> */
|
||||
/* Error code. 0~means success. */
|
||||
/* */
|
||||
/* <Note> */
|
||||
/* The `memory' parameter is a typeless pointer in order to avoid */
|
||||
/* un-wanted dependencies on the rest of the FreeType code. In */
|
||||
/* practice, it is an @SW_FT_Memory object, i.e., a handle to the */
|
||||
/* standard FreeType memory allocator. However, this field can be */
|
||||
/* completely ignored by a given raster implementation. */
|
||||
/* */
|
||||
typedef int
|
||||
(*SW_FT_Raster_NewFunc)( SW_FT_Raster* raster );
|
||||
|
||||
#define SW_FT_Raster_New_Func SW_FT_Raster_NewFunc
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <FuncType> */
|
||||
/* SW_FT_Raster_DoneFunc */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A function used to destroy a given raster object. */
|
||||
/* */
|
||||
/* <Input> */
|
||||
/* raster :: A handle to the raster object. */
|
||||
/* */
|
||||
typedef void
|
||||
(*SW_FT_Raster_DoneFunc)( SW_FT_Raster raster );
|
||||
|
||||
#define SW_FT_Raster_Done_Func SW_FT_Raster_DoneFunc
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <FuncType> */
|
||||
/* SW_FT_Raster_ResetFunc */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* FreeType provides an area of memory called the `render pool', */
|
||||
/* available to all registered rasters. This pool can be freely used */
|
||||
/* during a given scan-conversion but is shared by all rasters. Its */
|
||||
/* content is thus transient. */
|
||||
/* */
|
||||
/* This function is called each time the render pool changes, or just */
|
||||
/* after a new raster object is created. */
|
||||
/* */
|
||||
/* <Input> */
|
||||
/* raster :: A handle to the new raster object. */
|
||||
/* */
|
||||
/* pool_base :: The address in memory of the render pool. */
|
||||
/* */
|
||||
/* pool_size :: The size in bytes of the render pool. */
|
||||
/* */
|
||||
/* <Note> */
|
||||
/* Rasters can ignore the render pool and rely on dynamic memory */
|
||||
/* allocation if they want to (a handle to the memory allocator is */
|
||||
/* passed to the raster constructor). However, this is not */
|
||||
/* recommended for efficiency purposes. */
|
||||
/* */
|
||||
typedef void
|
||||
(*SW_FT_Raster_ResetFunc)( SW_FT_Raster raster,
|
||||
unsigned char* pool_base,
|
||||
unsigned long pool_size );
|
||||
|
||||
#define SW_FT_Raster_Reset_Func SW_FT_Raster_ResetFunc
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <FuncType> */
|
||||
/* SW_FT_Raster_RenderFunc */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* Invoke a given raster to scan-convert a given glyph image into a */
|
||||
/* target bitmap. */
|
||||
/* */
|
||||
/* <Input> */
|
||||
/* raster :: A handle to the raster object. */
|
||||
/* */
|
||||
/* params :: A pointer to an @SW_FT_Raster_Params structure used to */
|
||||
/* store the rendering parameters. */
|
||||
/* */
|
||||
/* <Return> */
|
||||
/* Error code. 0~means success. */
|
||||
/* */
|
||||
/* <Note> */
|
||||
/* The exact format of the source image depends on the raster's glyph */
|
||||
/* format defined in its @SW_FT_Raster_Funcs structure. It can be an */
|
||||
/* @SW_FT_Outline or anything else in order to support a large array of */
|
||||
/* glyph formats. */
|
||||
/* */
|
||||
/* Note also that the render function can fail and return a */
|
||||
/* `SW_FT_Err_Unimplemented_Feature' error code if the raster used does */
|
||||
/* not support direct composition. */
|
||||
/* */
|
||||
/* XXX: For now, the standard raster doesn't support direct */
|
||||
/* composition but this should change for the final release (see */
|
||||
/* the files `demos/src/ftgrays.c' and `demos/src/ftgrays2.c' */
|
||||
/* for examples of distinct implementations that support direct */
|
||||
/* composition). */
|
||||
/* */
|
||||
typedef int
|
||||
(*SW_FT_Raster_RenderFunc)( SW_FT_Raster raster,
|
||||
const SW_FT_Raster_Params* params );
|
||||
|
||||
#define SW_FT_Raster_Render_Func SW_FT_Raster_RenderFunc
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Struct> */
|
||||
/* SW_FT_Raster_Funcs */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A structure used to describe a given raster class to the library. */
|
||||
/* */
|
||||
/* <Fields> */
|
||||
/* glyph_format :: The supported glyph format for this raster. */
|
||||
/* */
|
||||
/* raster_new :: The raster constructor. */
|
||||
/* */
|
||||
/* raster_reset :: Used to reset the render pool within the raster. */
|
||||
/* */
|
||||
/* raster_render :: A function to render a glyph into a given bitmap. */
|
||||
/* */
|
||||
/* raster_done :: The raster destructor. */
|
||||
/* */
|
||||
typedef struct SW_FT_Raster_Funcs_
|
||||
{
|
||||
SW_FT_Raster_NewFunc raster_new;
|
||||
SW_FT_Raster_ResetFunc raster_reset;
|
||||
SW_FT_Raster_RenderFunc raster_render;
|
||||
SW_FT_Raster_DoneFunc raster_done;
|
||||
|
||||
} SW_FT_Raster_Funcs;
|
||||
|
||||
|
||||
extern const SW_FT_Raster_Funcs sw_ft_grays_raster;
|
||||
|
||||
#endif // SW_FT_IMG_H
|
||||
+1936
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,319 @@
|
||||
#ifndef SW_FT_STROKER_H
|
||||
#define SW_FT_STROKER_H
|
||||
/***************************************************************************/
|
||||
/* */
|
||||
/* ftstroke.h */
|
||||
/* */
|
||||
/* FreeType path stroker (specification). */
|
||||
/* */
|
||||
/* Copyright 2002-2006, 2008, 2009, 2011-2012 by */
|
||||
/* David Turner, Robert Wilhelm, and Werner Lemberg. */
|
||||
/* */
|
||||
/* This file is part of the FreeType project, and may only be used, */
|
||||
/* modified, and distributed under the terms of the FreeType project */
|
||||
/* license, LICENSE.TXT. By continuing to use, modify, or distribute */
|
||||
/* this file you indicate that you have read the license and */
|
||||
/* understand and accept it fully. */
|
||||
/* */
|
||||
/***************************************************************************/
|
||||
|
||||
#include "sw_ft_raster.h"
|
||||
|
||||
/**************************************************************
|
||||
*
|
||||
* @type:
|
||||
* SW_FT_Stroker
|
||||
*
|
||||
* @description:
|
||||
* Opaque handler to a path stroker object.
|
||||
*/
|
||||
typedef struct SW_FT_StrokerRec_* SW_FT_Stroker;
|
||||
|
||||
|
||||
/**************************************************************
|
||||
*
|
||||
* @enum:
|
||||
* SW_FT_Stroker_LineJoin
|
||||
*
|
||||
* @description:
|
||||
* These values determine how two joining lines are rendered
|
||||
* in a stroker.
|
||||
*
|
||||
* @values:
|
||||
* SW_FT_STROKER_LINEJOIN_ROUND ::
|
||||
* Used to render rounded line joins. Circular arcs are used
|
||||
* to join two lines smoothly.
|
||||
*
|
||||
* SW_FT_STROKER_LINEJOIN_BEVEL ::
|
||||
* Used to render beveled line joins. The outer corner of
|
||||
* the joined lines is filled by enclosing the triangular
|
||||
* region of the corner with a straight line between the
|
||||
* outer corners of each stroke.
|
||||
*
|
||||
* SW_FT_STROKER_LINEJOIN_MITER_FIXED ::
|
||||
* Used to render mitered line joins, with fixed bevels if the
|
||||
* miter limit is exceeded. The outer edges of the strokes
|
||||
* for the two segments are extended until they meet at an
|
||||
* angle. If the segments meet at too sharp an angle (such
|
||||
* that the miter would extend from the intersection of the
|
||||
* segments a distance greater than the product of the miter
|
||||
* limit value and the border radius), then a bevel join (see
|
||||
* above) is used instead. This prevents long spikes being
|
||||
* created. SW_FT_STROKER_LINEJOIN_MITER_FIXED generates a miter
|
||||
* line join as used in PostScript and PDF.
|
||||
*
|
||||
* SW_FT_STROKER_LINEJOIN_MITER_VARIABLE ::
|
||||
* SW_FT_STROKER_LINEJOIN_MITER ::
|
||||
* Used to render mitered line joins, with variable bevels if
|
||||
* the miter limit is exceeded. The intersection of the
|
||||
* strokes is clipped at a line perpendicular to the bisector
|
||||
* of the angle between the strokes, at the distance from the
|
||||
* intersection of the segments equal to the product of the
|
||||
* miter limit value and the border radius. This prevents
|
||||
* long spikes being created.
|
||||
* SW_FT_STROKER_LINEJOIN_MITER_VARIABLE generates a mitered line
|
||||
* join as used in XPS. SW_FT_STROKER_LINEJOIN_MITER is an alias
|
||||
* for SW_FT_STROKER_LINEJOIN_MITER_VARIABLE, retained for
|
||||
* backwards compatibility.
|
||||
*/
|
||||
typedef enum SW_FT_Stroker_LineJoin_
|
||||
{
|
||||
SW_FT_STROKER_LINEJOIN_ROUND = 0,
|
||||
SW_FT_STROKER_LINEJOIN_BEVEL = 1,
|
||||
SW_FT_STROKER_LINEJOIN_MITER_VARIABLE = 2,
|
||||
SW_FT_STROKER_LINEJOIN_MITER = SW_FT_STROKER_LINEJOIN_MITER_VARIABLE,
|
||||
SW_FT_STROKER_LINEJOIN_MITER_FIXED = 3
|
||||
|
||||
} SW_FT_Stroker_LineJoin;
|
||||
|
||||
|
||||
/**************************************************************
|
||||
*
|
||||
* @enum:
|
||||
* SW_FT_Stroker_LineCap
|
||||
*
|
||||
* @description:
|
||||
* These values determine how the end of opened sub-paths are
|
||||
* rendered in a stroke.
|
||||
*
|
||||
* @values:
|
||||
* SW_FT_STROKER_LINECAP_BUTT ::
|
||||
* The end of lines is rendered as a full stop on the last
|
||||
* point itself.
|
||||
*
|
||||
* SW_FT_STROKER_LINECAP_ROUND ::
|
||||
* The end of lines is rendered as a half-circle around the
|
||||
* last point.
|
||||
*
|
||||
* SW_FT_STROKER_LINECAP_SQUARE ::
|
||||
* The end of lines is rendered as a square around the
|
||||
* last point.
|
||||
*/
|
||||
typedef enum SW_FT_Stroker_LineCap_
|
||||
{
|
||||
SW_FT_STROKER_LINECAP_BUTT = 0,
|
||||
SW_FT_STROKER_LINECAP_ROUND,
|
||||
SW_FT_STROKER_LINECAP_SQUARE
|
||||
|
||||
} SW_FT_Stroker_LineCap;
|
||||
|
||||
|
||||
/**************************************************************
|
||||
*
|
||||
* @enum:
|
||||
* SW_FT_StrokerBorder
|
||||
*
|
||||
* @description:
|
||||
* These values are used to select a given stroke border
|
||||
* in @SW_FT_Stroker_GetBorderCounts and @SW_FT_Stroker_ExportBorder.
|
||||
*
|
||||
* @values:
|
||||
* SW_FT_STROKER_BORDER_LEFT ::
|
||||
* Select the left border, relative to the drawing direction.
|
||||
*
|
||||
* SW_FT_STROKER_BORDER_RIGHT ::
|
||||
* Select the right border, relative to the drawing direction.
|
||||
*
|
||||
* @note:
|
||||
* Applications are generally interested in the `inside' and `outside'
|
||||
* borders. However, there is no direct mapping between these and the
|
||||
* `left' and `right' ones, since this really depends on the glyph's
|
||||
* drawing orientation, which varies between font formats.
|
||||
*
|
||||
* You can however use @SW_FT_Outline_GetInsideBorder and
|
||||
* @SW_FT_Outline_GetOutsideBorder to get these.
|
||||
*/
|
||||
typedef enum SW_FT_StrokerBorder_
|
||||
{
|
||||
SW_FT_STROKER_BORDER_LEFT = 0,
|
||||
SW_FT_STROKER_BORDER_RIGHT
|
||||
|
||||
} SW_FT_StrokerBorder;
|
||||
|
||||
|
||||
/**************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Stroker_New
|
||||
*
|
||||
* @description:
|
||||
* Create a new stroker object.
|
||||
*
|
||||
* @input:
|
||||
* library ::
|
||||
* FreeType library handle.
|
||||
*
|
||||
* @output:
|
||||
* astroker ::
|
||||
* A new stroker object handle. NULL in case of error.
|
||||
*
|
||||
* @return:
|
||||
* FreeType error code. 0~means success.
|
||||
*/
|
||||
SW_FT_Error
|
||||
SW_FT_Stroker_New( SW_FT_Stroker *astroker );
|
||||
|
||||
|
||||
/**************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Stroker_Set
|
||||
*
|
||||
* @description:
|
||||
* Reset a stroker object's attributes.
|
||||
*
|
||||
* @input:
|
||||
* stroker ::
|
||||
* The target stroker handle.
|
||||
*
|
||||
* radius ::
|
||||
* The border radius.
|
||||
*
|
||||
* line_cap ::
|
||||
* The line cap style.
|
||||
*
|
||||
* line_join ::
|
||||
* The line join style.
|
||||
*
|
||||
* miter_limit ::
|
||||
* The miter limit for the SW_FT_STROKER_LINEJOIN_MITER_FIXED and
|
||||
* SW_FT_STROKER_LINEJOIN_MITER_VARIABLE line join styles,
|
||||
* expressed as 16.16 fixed-point value.
|
||||
*
|
||||
* @note:
|
||||
* The radius is expressed in the same units as the outline
|
||||
* coordinates.
|
||||
*/
|
||||
void
|
||||
SW_FT_Stroker_Set( SW_FT_Stroker stroker,
|
||||
SW_FT_Fixed radius,
|
||||
SW_FT_Stroker_LineCap line_cap,
|
||||
SW_FT_Stroker_LineJoin line_join,
|
||||
SW_FT_Fixed miter_limit );
|
||||
|
||||
/**************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Stroker_ParseOutline
|
||||
*
|
||||
* @description:
|
||||
* A convenience function used to parse a whole outline with
|
||||
* the stroker. The resulting outline(s) can be retrieved
|
||||
* later by functions like @SW_FT_Stroker_GetCounts and @SW_FT_Stroker_Export.
|
||||
*
|
||||
* @input:
|
||||
* stroker ::
|
||||
* The target stroker handle.
|
||||
*
|
||||
* outline ::
|
||||
* The source outline.
|
||||
*
|
||||
*
|
||||
* @return:
|
||||
* FreeType error code. 0~means success.
|
||||
*
|
||||
* @note:
|
||||
* If `opened' is~0 (the default), the outline is treated as a closed
|
||||
* path, and the stroker generates two distinct `border' outlines.
|
||||
*
|
||||
*
|
||||
* This function calls @SW_FT_Stroker_Rewind automatically.
|
||||
*/
|
||||
SW_FT_Error
|
||||
SW_FT_Stroker_ParseOutline( SW_FT_Stroker stroker,
|
||||
const SW_FT_Outline* outline);
|
||||
|
||||
|
||||
/**************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Stroker_GetCounts
|
||||
*
|
||||
* @description:
|
||||
* Call this function once you have finished parsing your paths
|
||||
* with the stroker. It returns the number of points and
|
||||
* contours necessary to export all points/borders from the stroked
|
||||
* outline/path.
|
||||
*
|
||||
* @input:
|
||||
* stroker ::
|
||||
* The target stroker handle.
|
||||
*
|
||||
* @output:
|
||||
* anum_points ::
|
||||
* The number of points.
|
||||
*
|
||||
* anum_contours ::
|
||||
* The number of contours.
|
||||
*
|
||||
* @return:
|
||||
* FreeType error code. 0~means success.
|
||||
*/
|
||||
SW_FT_Error
|
||||
SW_FT_Stroker_GetCounts( SW_FT_Stroker stroker,
|
||||
SW_FT_UInt *anum_points,
|
||||
SW_FT_UInt *anum_contours );
|
||||
|
||||
|
||||
/**************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Stroker_Export
|
||||
*
|
||||
* @description:
|
||||
* Call this function after @SW_FT_Stroker_GetBorderCounts to
|
||||
* export all borders to your own @SW_FT_Outline structure.
|
||||
*
|
||||
* Note that this function appends the border points and
|
||||
* contours to your outline, but does not try to resize its
|
||||
* arrays.
|
||||
*
|
||||
* @input:
|
||||
* stroker ::
|
||||
* The target stroker handle.
|
||||
*
|
||||
* outline ::
|
||||
* The target outline handle.
|
||||
*/
|
||||
void
|
||||
SW_FT_Stroker_Export( SW_FT_Stroker stroker,
|
||||
SW_FT_Outline* outline );
|
||||
|
||||
|
||||
/**************************************************************
|
||||
*
|
||||
* @function:
|
||||
* SW_FT_Stroker_Done
|
||||
*
|
||||
* @description:
|
||||
* Destroy a stroker object.
|
||||
*
|
||||
* @input:
|
||||
* stroker ::
|
||||
* A stroker handle. Can be NULL.
|
||||
*/
|
||||
void
|
||||
SW_FT_Stroker_Done( SW_FT_Stroker stroker );
|
||||
|
||||
|
||||
#endif // SW_FT_STROKER_H
|
||||
+160
@@ -0,0 +1,160 @@
|
||||
#ifndef SW_FT_TYPES_H
|
||||
#define SW_FT_TYPES_H
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_Fixed */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* This type is used to store 16.16 fixed-point values, like scaling */
|
||||
/* values or matrix coefficients. */
|
||||
/* */
|
||||
typedef signed long SW_FT_Fixed;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_Int */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A typedef for the int type. */
|
||||
/* */
|
||||
typedef signed int SW_FT_Int;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_UInt */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A typedef for the unsigned int type. */
|
||||
/* */
|
||||
typedef unsigned int SW_FT_UInt;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_Long */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A typedef for signed long. */
|
||||
/* */
|
||||
typedef signed long SW_FT_Long;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_ULong */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A typedef for unsigned long. */
|
||||
/* */
|
||||
typedef unsigned long SW_FT_ULong;
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_Short */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A typedef for signed short. */
|
||||
/* */
|
||||
typedef signed short SW_FT_Short;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_Byte */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A simple typedef for the _unsigned_ char type. */
|
||||
/* */
|
||||
typedef unsigned char SW_FT_Byte;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_Bool */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A typedef of unsigned char, used for simple booleans. As usual, */
|
||||
/* values 1 and~0 represent true and false, respectively. */
|
||||
/* */
|
||||
typedef unsigned char SW_FT_Bool;
|
||||
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_Error */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* The FreeType error code type. A value of~0 is always interpreted */
|
||||
/* as a successful operation. */
|
||||
/* */
|
||||
typedef int SW_FT_Error;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Type> */
|
||||
/* SW_FT_Pos */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* The type SW_FT_Pos is used to store vectorial coordinates. Depending */
|
||||
/* on the context, these can represent distances in integer font */
|
||||
/* units, or 16.16, or 26.6 fixed-point pixel coordinates. */
|
||||
/* */
|
||||
typedef signed long SW_FT_Pos;
|
||||
|
||||
|
||||
/*************************************************************************/
|
||||
/* */
|
||||
/* <Struct> */
|
||||
/* SW_FT_Vector */
|
||||
/* */
|
||||
/* <Description> */
|
||||
/* A simple structure used to store a 2D vector; coordinates are of */
|
||||
/* the SW_FT_Pos type. */
|
||||
/* */
|
||||
/* <Fields> */
|
||||
/* x :: The horizontal coordinate. */
|
||||
/* y :: The vertical coordinate. */
|
||||
/* */
|
||||
typedef struct SW_FT_Vector_
|
||||
{
|
||||
SW_FT_Pos x;
|
||||
SW_FT_Pos y;
|
||||
|
||||
} SW_FT_Vector;
|
||||
|
||||
|
||||
typedef long long int SW_FT_Int64;
|
||||
typedef unsigned long long int SW_FT_UInt64;
|
||||
|
||||
typedef signed int SW_FT_Int32;
|
||||
typedef unsigned int SW_FT_UInt32;
|
||||
|
||||
|
||||
#define SW_FT_BOOL( x ) ( (SW_FT_Bool)( x ) )
|
||||
|
||||
#define SW_FT_SIZEOF_LONG 4
|
||||
|
||||
#ifndef TRUE
|
||||
#define TRUE 1
|
||||
#endif
|
||||
|
||||
#ifndef FALSE
|
||||
#define FALSE 0
|
||||
#endif
|
||||
|
||||
|
||||
#endif // SW_FT_TYPES_H
|
||||
@@ -0,0 +1,64 @@
|
||||
|
||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||
# Visual Studio Version 17
|
||||
VisualStudioVersion = 17.1.32319.34
|
||||
MinimumVisualStudioVersion = 10.0.40219.1
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "shared", "shared\shared.vcxitems", "{096F9029-DBBB-4CB7-A0C5-615007DCA000}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "dll", "dll\Shell.vcxproj", "{BAF011AC-D5E9-42C5-BA26-BA6115A45DAC}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "exe", "exe\exe.vcxproj", "{FFFD0DDB-48FB-4681-A3B6-8E787FA98C98}"
|
||||
EndProject
|
||||
Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ca", "setup\ca\ca.vcxproj", "{F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}"
|
||||
EndProject
|
||||
Project("{B7DD6F7E-DEF8-4E67-B5B7-07EF123DB6F0}") = "setup", "setup\wix\setup.wixproj", "{F8A8D368-F53D-4EA1-9E17-404DA0CC89CD}"
|
||||
ProjectSection(ProjectDependencies) = postProject
|
||||
{BAF011AC-D5E9-42C5-BA26-BA6115A45DAC} = {BAF011AC-D5E9-42C5-BA26-BA6115A45DAC}
|
||||
{F72D34CA-48DA-4DFD-91A9-A0C78BEF6981} = {F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}
|
||||
{FFFD0DDB-48FB-4681-A3B6-8E787FA98C98} = {FFFD0DDB-48FB-4681-A3B6-8E787FA98C98}
|
||||
EndProjectSection
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
release|ARM64 = release|ARM64
|
||||
release|x64 = release|x64
|
||||
release|x86 = release|x86
|
||||
EndGlobalSection
|
||||
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||
{BAF011AC-D5E9-42C5-BA26-BA6115A45DAC}.release|ARM64.ActiveCfg = release|ARM64
|
||||
{BAF011AC-D5E9-42C5-BA26-BA6115A45DAC}.release|ARM64.Build.0 = release|ARM64
|
||||
{BAF011AC-D5E9-42C5-BA26-BA6115A45DAC}.release|x64.ActiveCfg = release|x64
|
||||
{BAF011AC-D5E9-42C5-BA26-BA6115A45DAC}.release|x64.Build.0 = release|x64
|
||||
{BAF011AC-D5E9-42C5-BA26-BA6115A45DAC}.release|x86.ActiveCfg = release|Win32
|
||||
{BAF011AC-D5E9-42C5-BA26-BA6115A45DAC}.release|x86.Build.0 = release|Win32
|
||||
{FFFD0DDB-48FB-4681-A3B6-8E787FA98C98}.release|ARM64.ActiveCfg = release|ARM64
|
||||
{FFFD0DDB-48FB-4681-A3B6-8E787FA98C98}.release|ARM64.Build.0 = release|ARM64
|
||||
{FFFD0DDB-48FB-4681-A3B6-8E787FA98C98}.release|x64.ActiveCfg = release|x64
|
||||
{FFFD0DDB-48FB-4681-A3B6-8E787FA98C98}.release|x64.Build.0 = release|x64
|
||||
{FFFD0DDB-48FB-4681-A3B6-8E787FA98C98}.release|x86.ActiveCfg = release|Win32
|
||||
{FFFD0DDB-48FB-4681-A3B6-8E787FA98C98}.release|x86.Build.0 = release|Win32
|
||||
{F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.release|ARM64.ActiveCfg = release|ARM64
|
||||
{F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.release|ARM64.Build.0 = release|ARM64
|
||||
{F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.release|x64.ActiveCfg = release|x64
|
||||
{F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.release|x64.Build.0 = release|x64
|
||||
{F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.release|x86.ActiveCfg = release|Win32
|
||||
{F72D34CA-48DA-4DFD-91A9-A0C78BEF6981}.release|x86.Build.0 = release|Win32
|
||||
{F8A8D368-F53D-4EA1-9E17-404DA0CC89CD}.release|ARM64.ActiveCfg = Release|ARM64
|
||||
{F8A8D368-F53D-4EA1-9E17-404DA0CC89CD}.release|ARM64.Build.0 = Release|ARM64
|
||||
{F8A8D368-F53D-4EA1-9E17-404DA0CC89CD}.release|x64.ActiveCfg = Release|x64
|
||||
{F8A8D368-F53D-4EA1-9E17-404DA0CC89CD}.release|x64.Build.0 = Release|x64
|
||||
{F8A8D368-F53D-4EA1-9E17-404DA0CC89CD}.release|x86.ActiveCfg = Release|x86
|
||||
{F8A8D368-F53D-4EA1-9E17-404DA0CC89CD}.release|x86.Build.0 = Release|x86
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
SolutionGuid = {EE8CC431-4AA1-4CF6-B3CE-AD27E8B980E8}
|
||||
EndGlobalSection
|
||||
GlobalSection(SharedMSBuildProjectFiles) = preSolution
|
||||
shared\shared.vcxitems*{096f9029-dbbb-4cb7-a0c5-615007dca000}*SharedItemsImports = 9
|
||||
shared\shared.vcxitems*{baf011ac-d5e9-42c5-ba26-ba6115a45dac}*SharedItemsImports = 4
|
||||
shared\shared.vcxitems*{fffd0ddb-48fb-4681-a3b6-8e787fa98c98}*SharedItemsImports = 4
|
||||
EndGlobalSection
|
||||
EndGlobal
|
||||
@@ -0,0 +1,41 @@
|
||||
menu(mode="multiple" title=loc.develop sep=sep.bottom image=\uE26E)
|
||||
{
|
||||
menu(mode="single" title=loc.editors image=\uE17A)
|
||||
{
|
||||
item(title='Visual Studio Code' image=[\uE272, #22A7F2] cmd='code' args='"@sel.path"')
|
||||
separator
|
||||
item(type='file' mode="single" title=loc.windows_notepad image cmd='@sys.bin\notepad.exe' args='"@sel.path"')
|
||||
}
|
||||
|
||||
menu(mode="multiple" title='dotnet' image=\uE143)
|
||||
{
|
||||
item(title='run' cmd-line='/K dotnet run' image=\uE149)
|
||||
item(title='watch' cmd-line='/K dotnet watch')
|
||||
item(title='clean' image=\uE0CE cmd-line='/K dotnet clean')
|
||||
separator
|
||||
item(title='build debug' cmd-line='/K dotnet build')
|
||||
item(title='build release' cmd-line='/K dotnet build -c release /p:DebugType=None')
|
||||
|
||||
menu(mode="multiple" sep="both" title='publish' image=\ue11f)
|
||||
{
|
||||
$publish='dotnet publish -r win-x64 -c release --output publish /*/p:CopyOutputSymbolsToPublishDirectory=false*/'
|
||||
item(title='publish sinale file' sep="after" cmd-line='/K @publish --no-self-contained /p:PublishSingleFile=true')
|
||||
item(title='framework-dependent deployment' cmd-line='/K @publish')
|
||||
item(title='framework-dependent executable' cmd-line='/K @publish --self-contained false')
|
||||
item(title='self-contained deployment' cmd-line='/K @publish --self-contained true')
|
||||
item(title='single-file' cmd-line='/K @publish /p:PublishSingleFile=true /p:PublishTrimmed=false')
|
||||
item(title='single-file-trimmed' cmd-line='/K @publish /p:PublishSingleFile=true /p:PublishTrimmed=true')
|
||||
}
|
||||
|
||||
item(title='ef migrations add InitialCreate' cmd-line='/K dotnet ef migrations add InitialCreate')
|
||||
item(title='ef database update' cmd-line='/K dotnet ef database update')
|
||||
separator
|
||||
item(title='help' image=\uE136 cmd-line='/k dotnet -h')
|
||||
item(title='version' cmd-line='/k dotnet --info')
|
||||
}
|
||||
|
||||
item(type="file" title="reshack" sep="top" image cmd='D:\config\Programs\dev\petools\resource\reshack\reshack.exe' args=sel(1))
|
||||
item(type="file" title="peview" image cmd='D:\config\Programs\dev\petools\peview.exe' args=sel(1))
|
||||
|
||||
item(type="dir|dir.back" title="Web server" vis=key.shift() cmd='D:\config\Programs\dev\web\HTTPServer\WebServer.exe' args='-open -path:"@sel.path"')
|
||||
}
|
||||
@@ -0,0 +1,80 @@
|
||||
menu(where=sel.count>0 type='file|dir|drive|namespace|back' mode="multiple" title=loc.file_manage image=\uE253)
|
||||
{
|
||||
menu(separator="after" title=title.copy_path image=icon.copy_path)
|
||||
{
|
||||
item(where=sel.count > 1 title=loc.copy_multiple_paths cmd=command.copy(sel(false, "\n")))
|
||||
item(mode="single" title=@sel.path tip=sel.path cmd=command.copy(sel.path))
|
||||
item(mode="single" type='file' separator="before" where=length(sel.lnk)>0 title=sel.lnk cmd=command.copy(sel.lnk))
|
||||
separator
|
||||
item(mode="single" where=@sel.parent.len>3 title=sel.parent cmd=@command.copy(sel.parent))
|
||||
separator
|
||||
item(mode="single" type='file|dir|back.dir' title=sel.file.name cmd=command.copy(sel.file.name))
|
||||
item(mode="single" type='file' where=sel.file.len != sel.file.title.len title=@sel.file.title cmd=command.copy(sel.file.title))
|
||||
item(mode="single" type='file' where=sel.file.ext.len>0 title=sel.file.ext cmd=command.copy(sel.file.ext))
|
||||
}
|
||||
|
||||
item(mode="single" type="file" title=loc.change_extension image=\uE0B5 cmd=if(input(loc.change_extension, "Type extension"),
|
||||
io.rename(sel.path, path.join(sel.dir, sel.file.title + "." + input.result))))
|
||||
|
||||
menu(separator="after" image=\uE290 title=title.select)
|
||||
{
|
||||
item(title=loc.all image=icon.select_all cmd=command.select_all)
|
||||
item(title=loc.invert image=icon.invert_selection cmd=command.invert_selection)
|
||||
item(title=loc.none image=icon.select_none cmd=command.select_none)
|
||||
}
|
||||
|
||||
item(type='file|dir|back.dir|drive' title=loc.take_ownership image=[\uE194,#f00] admin
|
||||
cmd args='/K takeown /f "@sel.path" @if(sel.type==1,null,"/r /d y") && icacls "@sel.path" /grant *S-1-5-32-544:F @if(sel.type==1,"/c /l","/t /c /l /q")')
|
||||
separator
|
||||
menu(title=loc.show_hide image=icon.show_hidden_files)
|
||||
{
|
||||
item(title=loc.system_files image=inherit cmd='@command.togglehidden')
|
||||
item(title=loc.file_name_extensions image=icon.show_file_extensions cmd='@command.toggleext')
|
||||
}
|
||||
|
||||
menu(type='file|dir|back.dir' mode="single" title=loc.attributes image=icon.properties)
|
||||
{
|
||||
$atrr = io.attributes(sel.path)
|
||||
item(title=loc.hidden checked=io.attribute.hidden(atrr)
|
||||
cmd args='/c ATTRIB @if(io.attribute.hidden(atrr),"-","+")H "@sel.path"' window=hidden)
|
||||
|
||||
item(title=loc.system checked=io.attribute.system(atrr)
|
||||
cmd args='/c ATTRIB @if(io.attribute.system(atrr),"-","+")S "@sel.path"' window=hidden)
|
||||
|
||||
item(title=loc.readonly checked=io.attribute.readonly(atrr)
|
||||
cmd args='/c ATTRIB @if(io.attribute.readonly(atrr),"-","+")R "@sel.path"' window=hidden)
|
||||
|
||||
item(title=loc.archive checked=io.attribute.archive(atrr)
|
||||
cmd args='/c ATTRIB @if(io.attribute.archive(atrr),"-","+")A "@sel.path"' window=hidden)
|
||||
separator
|
||||
item(title=loc.created keys=io.dt.created(sel.path, 'y/m/d') cmd=io.dt.created(sel.path,2000,1,1) vis=label)
|
||||
item(title=loc.modified keys=io.dt.modified(sel.path, 'y/m/d') cmd=io.dt.modified(sel.path,2000,1,1) vis=label)
|
||||
item(title=loc.accessed keys=io.dt.accessed(sel.path, 'y/m/d') cmd=io.dt.accessed(sel.path,2000,1,1) vis=label)
|
||||
}
|
||||
|
||||
menu(mode="single" type='file' find='.dll|.ocx' separator="before" title=loc.register_server image=\uea86)
|
||||
{
|
||||
item(title=loc.register admin cmd='regsvr32.exe' args='@sel.path.quote' invoke="multiple")
|
||||
item(title=loc.unregister admin cmd='regsvr32.exe' args='/u @sel.path.quote' invoke="multiple")
|
||||
}
|
||||
|
||||
menu(mode="single" type='back' expanded=true)
|
||||
{
|
||||
menu(separator="before" title=loc.new_folder image=icon.new_folder)
|
||||
{
|
||||
item(title=loc.datetime cmd=io.dir.create(sys.datetime("ymdHMSs")))
|
||||
item(title=loc.guid cmd=io.dir.create(str.guid))
|
||||
}
|
||||
|
||||
menu(title=loc.new_file image=icon.new_file)
|
||||
{
|
||||
$dt = sys.datetime("ymdHMSs")
|
||||
item(title='TXT' cmd=io.file.create('@(dt).txt', 'Hello World!'))
|
||||
item(title='XML' cmd=io.file.create('@(dt).xml', '<root>Hello World!</root>'))
|
||||
item(title='JSON' cmd=io.file.create('@(dt).json', '[]'))
|
||||
item(title='HTML' cmd=io.file.create('@(dt).html', "<html>\n\t<head>\n\t</head>\n\t<body>Hello World!\n\t</body>\n</html>"))
|
||||
}
|
||||
}
|
||||
|
||||
item(where=!wnd.is_desktop title=title.folder_options image=icon.folder_options cmd=command.folder_options)
|
||||
}
|
||||
@@ -0,0 +1,62 @@
|
||||
menu(type='*' where=window.is_taskbar||sel.count mode=mode.multiple title=title.go_to sep=sep.both image=\uE14A)
|
||||
{
|
||||
menu(title=loc.folder image=\uE1F4)
|
||||
{
|
||||
item(title='Windows' image=inherit cmd=sys.dir)
|
||||
item(title='System' image=inherit cmd=sys.bin)
|
||||
item(title='Program Files' image=inherit cmd=sys.prog)
|
||||
item(title='Program Files x86' image=inherit cmd=sys.prog32)
|
||||
item(title='ProgramData' image=inherit cmd=sys.programdata)
|
||||
item(title='Applications' image=inherit cmd='shell:appsfolder')
|
||||
item(title='Users' image=inherit cmd=sys.users)
|
||||
separator
|
||||
//item(title='@user.name@@@sys.name' vis=label)
|
||||
item(title='Desktop' image=inherit cmd=user.desktop)
|
||||
item(title='Downloads' image=inherit cmd=user.downloads)
|
||||
item(title='Pictures' image=inherit cmd=user.pictures)
|
||||
item(title='Documents' image=inherit cmd=user.documents)
|
||||
item(title='Startmenu' image=inherit cmd=user.startmenu)
|
||||
item(title='Profile' image=inherit cmd=user.dir)
|
||||
item(title='AppData' image=inherit cmd=user.appdata)
|
||||
item(title='Temp' image=inherit cmd=user.temp)
|
||||
}
|
||||
item(title=title.control_panel image=\uE0F3 cmd='shell:::{5399E694-6CE5-4D6C-8FCE-1D8870FDCBA0}')
|
||||
item(title=loc.all_control_panel_items image=\uE0F3 cmd='shell:::{ED7BA470-8E54-465E-825C-99712043E01C}')
|
||||
item(title=title.run image=\uE14B cmd='shell:::{2559a1f3-21d7-11d4-bdaf-00c04f60b9f0}')
|
||||
menu(where=sys.ver.major >= 10 title=title.settings sep=sep.before image=\uE0F3)
|
||||
{
|
||||
// https://docs.microsoft.com/en-us/windows/uwp/launch-resume/launch-settings-app
|
||||
item(title=loc.system image=inherit cmd='ms-settings:')
|
||||
item(title=loc.about image=inherit cmd='ms-settings:about')
|
||||
item(title=loc.your_info image=inherit cmd='ms-settings:yourinfo')
|
||||
item(title=loc.system_info image=inherit cmd-line='/K systeminfo')
|
||||
item(title=loc.search cmd='search-ms:' image=inherit)
|
||||
item(title=loc.usb image=inherit cmd='ms-settings:usb')
|
||||
item(title=loc.windows_update image=inherit cmd='ms-settings:windowsupdate')
|
||||
item(title=loc.windows_defender image=inherit cmd='ms-settings:windowsdefender')
|
||||
menu(title=loc.apps image=inherit)
|
||||
{
|
||||
item(title=loc.apps_features image=inherit cmd='ms-settings:appsfeatures')
|
||||
item(title=loc.default_apps image=inherit cmd='ms-settings:defaultapps')
|
||||
item(title=loc.optional_features image=inherit cmd='ms-settings:optionalfeatures')
|
||||
item(title=loc.startup image=inherit cmd='ms-settings:startupapps')
|
||||
}
|
||||
menu(title=loc.personalization image=inherit)
|
||||
{
|
||||
item(title=loc.personalization image=inherit cmd='ms-settings:personalization')
|
||||
item(title=loc.lockscreen image=inherit cmd='ms-settings:lockscreen')
|
||||
item(title=loc.background image=inherit cmd='ms-settings:personalization-background')
|
||||
item(title=loc.colors image=inherit cmd='ms-settings:colors')
|
||||
item(title=loc.themes image=inherit cmd='ms-settings:themes')
|
||||
item(title=loc.start image=inherit cmd='ms-settings:personalization-start')
|
||||
item(title=loc.taskbar image=inherit cmd='ms-settings:taskbar')
|
||||
}
|
||||
menu(title=loc.network image=inherit)
|
||||
{
|
||||
item(title=loc.status image=inherit cmd='ms-settings:network-status')
|
||||
item(title=loc.ethernet image=inherit cmd='ms-settings:network-ethernet')
|
||||
item(title=loc.wifi image=inherit cmd='ms-settings:network-wifi')
|
||||
item(title=loc.connections image=inherit cmd='shell:::{7007ACC7-3202-11D1-AAD2-00805FC1270E}')
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,682 @@
|
||||
$color3 = @if(theme.islight,image.color3,'none')
|
||||
$color_islight_WB = @if(theme.islight,'#fff','#000')
|
||||
$clipPath='<defs><clipPath id="clip0"><path fill="#fff" d="M0 0h16v16H0z"/></clipPath></defs>'
|
||||
$svg_window_template2='<path fill="@image.color1" d="M3.453 15C3.12 15 2.805 14.93 2.508 14.8C2.508 14.8 2.211 14.66 1.953 14.48C1.953 14.48 1.734 14.27 1.516 14.05C1.516 14.05 1.339 13.79 1.203 13.49C1.203 13.49 1.068 13.2 1 12.88L1 3.438C1 3.115 1.068 2.805 1.203 2.508C1.203 2.508 1.339 2.211 1.516 1.951C1.516 1.951 1.734 1.727 1.953 1.503C1.953 1.503 2.211 1.326 2.508 1.195C2.508 1.195 2.805 1.065 3.12 1L12.56 1C12.89 1 13.2 1.065 13.49 1.195C13.49 1.195 13.79 1.326 14.05 1.503C14.05 1.503 14.27 1.727 14.5 1.951C14.5 1.951 14.67 2.211 14.8 2.508C14.8 2.508 14.93 2.805 15 3.115L15 6.938C14.84 6.812 14.68 6.7 14.52 6.602C14.52 6.602 14.35 6.503 14.18 6.406L14 5L2 5L2 12.5C2 12.7 2.039 12.89 2.117 13.07C2.117 13.07 2.195 13.25 2.305 13.41C2.305 13.41 2.445 13.55 2.586 13.7C2.586 13.7 2.747 13.8 2.93 13.88C2.93 13.88 3.112 13.96 3.302 14L6.328 14C6.412 14.18 6.505 14.35 6.609 14.52C6.609 14.52 6.714 14.68 6.823 14.84ZM2 4L14 4L14 3.5C14 3.292 13.96 3.096 13.88 2.914C13.88 2.914 13.8 2.732 13.7 2.573C13.7 2.573 13.56 2.438 13.43 2.302C13.43 2.302 13.27 2.195 13.09 2.117C13.09 2.117 12.9 2.039 12.71 2L3.5 2C3.302 2 3.112 2.039 2.93 2.117C2.93 2.117 2.747 2.195 2.586 2.302C2.586 2.302 2.445 2.438 2.305 2.573C2.305 2.573 2.195 2.732 2.117 2.914C2.117 2.914 2.039 3.096 2 3.292Z"/>'
|
||||
$svg_window_template='<path fill="@image.color1" d="M3.453 15C3.12 15 2.805 14.93 2.508 14.8C2.508 14.8 2.211 14.66 1.953 14.48C1.953 14.48 1.734 14.27 1.516 14.05C1.516 14.05 1.339 13.79 1.203 13.49C1.203 13.49 1.068 13.2 1 12.88L1 3.438C1 3.115 1.068 2.805 1.203 2.508C1.203 2.508 1.339 2.211 1.516 1.951C1.516 1.951 1.734 1.727 1.953 1.503C1.953 1.503 2.211 1.326 2.508 1.195C2.508 1.195 2.805 1.065 3.12 1L12.56 1C12.89 1 13.2 1.065 13.49 1.195C13.49 1.195 13.79 1.326 14.05 1.503C14.05 1.503 14.27 1.727 14.5 1.951C14.5 1.951 14.67 2.211 14.8 2.508C14.8 2.508 14.93 2.805 15 3.115L15 12.55C15 12.88 14.93 13.2 14.8 13.49C14.8 13.49 14.67 13.79 14.5 14.05C14.5 14.05 14.27 14.27 14.05 14.48C14.05 14.48 13.79 14.66 13.49 14.8C13.49 14.8 13.2 14.93 12.89 15ZM2 4L14 4L14 3.5C14 3.292 13.96 3.096 13.88 2.914C13.88 2.914 13.8 2.732 13.7 2.573C13.7 2.573 13.56 2.438 13.43 2.302C13.43 2.302 13.27 2.195 13.09 2.117C13.09 2.117 12.9 2.039 12.71 2L3.5 2C3.302 2 3.112 2.039 2.93 2.117C2.93 2.117 2.747 2.195 2.586 2.302C2.586 2.302 2.445 2.438 2.305 2.573C2.305 2.573 2.195 2.732 2.117 2.914C2.117 2.914 2.039 3.096 2 3.292ZM12.5 14C12.71 14 12.9 13.96 13.09 13.88C13.09 13.88 13.27 13.8 13.43 13.7C13.43 13.7 13.56 13.55 13.7 13.41C13.7 13.41 13.8 13.25 13.88 13.07C13.88 13.07 13.96 12.89 14 12.7L14 5L2 5L2 12.5C2 12.7 2.039 12.89 2.117 13.07C2.117 13.07 2.195 13.25 2.305 13.41C2.305 13.41 2.445 13.55 2.586 13.7C2.586 13.7 2.747 13.8 2.93 13.88C2.93 13.88 3.112 13.96 3.302 14Z"/>'
|
||||
|
||||
@copy,copy_to_clipboard='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M5 4.5H3.5a2 2 0 00-2 2v6a2 2 0 002 2h4A2 2 0 009.43 13H8a3 3 0 01-3-3V4.5z"/>
|
||||
<path fill="@image.color1" d="M5 4H3.5A2.5 2.5 0 001 6.5v6A2.5 2.5 0 003.5 15h4a2.5 2.5 0 002.45-2H8.91A1.5 1.5 0 017.5 14h-4A1.5 1.5 0 012 12.5v-6A1.5 1.5 0 013.5 5H5V4z"/>
|
||||
<path fill="@color3" d="M6.5 9.5v-6a2 2 0 012-2h4a2 2 0 012 2v6a2 2 0 01-2 2h-4a2 2 0 01-2-2z"/>
|
||||
<path fill="@image.color2" d="M8.5 2A1.5 1.5 0 007 3.5v6A1.5 1.5 0 008.5 11h4A1.5 1.5 0 0014 9.5v-6A1.5 1.5 0 0012.5 2h-4zM6 3.5A2.5 2.5 0 018.5 1h4A2.5 2.5 0 0115 3.5v6a2.5 2.5 0 01-2.5 2.5h-4A2.5 2.5 0 016 9.5v-6z"/>
|
||||
</svg>'
|
||||
|
||||
@cut='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@image.color1" d="M3.22.08a.5.5 0 01.69.14l6.82 10.49a.5.5 0 11-.83.54L3.08.77a.5.5 0 01.14-.69z"/>
|
||||
<path fill="@image.color1" d="M7.85 6.74l-2.59 4a.5.5 0 00.83.54L8.45 7.66l-.59-.91zm1.34-.23L12.92.77a.5.5 0 00-.83-.54L8.59 5.59l.59.91z"/>
|
||||
<path fill="@image.color2" d="M4 11a2 2 0 100 4 2 2 0 000-4zm-3 2a3 3 0 116 0 3 3 0 01-6 0zm11-2a2 2 0 100 4 2 2 0 000-4zm-3 2a3 3 0 116 0 3 3 0 01-6 0z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@paste='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M2.5 1.5h2a1 1 0 011-1h3a1 1 0 011 1h2a1 1 0 011 1V4H8a2 2 0 00-2 2v9.5H2.5a1 1 0 01-1-1v-12a1 1 0 011-1z"/>
|
||||
<path fill="@image.color1" d="M2.5 2a.5.5 0 00-.5.5v12a.5.5 0 00.5.5h3a.5.5 0 010 1h-3A1.5 1.5 0 011 14.5v-12A1.5 1.5 0 012.5 1h2a.5.5 0 010 1h-2zM9 1.5a.5.5 0 01.5-.5h2A1.5 1.5 0 0113 2.5v1a.5.5 0 01-1 0v-1a.5.5 0 00-.5-.5h-2a.5.5 0 01-.5-.5z"/>
|
||||
<path fill="@image.color1" d="M4 1.5A1.5 1.5 0 015.5 0h3a1.5 1.5 0 110 3h-3A1.5 1.5 0 014 1.5zM5.5 1a.5.5 0 000 1h3a.5.5 0 000-1h-3z"/>
|
||||
<path fill="@color3" d="M13.5 5.5h-5a1 1 0 00-1 1v8a1 1 0 001 1h5a1 1 0 001-1v-8a1 1 0 00-1-1z"/>
|
||||
<path fill="@image.color2" d="M7 6.5A1.5 1.5 0 018.5 5h5A1.5 1.5 0 0115 6.5v8a1.5 1.5 0 01-1.5 1.5h-5A1.5 1.5 0 017 14.5v-8zM8.5 6a.5.5 0 00-.5.5v8a.5.5 0 00.5.5h5a.5.5 0 00.5-.5v-8a.5.5 0 00-.5-.5h-5z"/>
|
||||
</svg>'
|
||||
|
||||
@paste_shortcut='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M3.5 1.5h2a1 1 0 011-1h3a1 1 0 011 1h2a1 1 0 011 1V7H9a2 2 0 00-2 2v6.5H3.5a1 1 0 01-1-1v-12a1 1 0 011-1z"/>
|
||||
<path fill="@image.color1" d="M3.5 2a.5.5 0 00-.5.5v12a.5.5 0 00.5.5h3a.5.5 0 010 1h-3A1.5 1.5 0 012 14.5v-12A1.5 1.5 0 013.5 1h2a.5.5 0 010 1h-2zm6.5-.5a.5.5 0 01.5-.5h2A1.5 1.5 0 0114 2.5v4a.5.5 0 01-1 0v-4a.5.5 0 00-.5-.5h-2a.5.5 0 01-.5-.5z"/>
|
||||
<path fill="@image.color1" d="M5 1.5A1.5 1.5 0 016.5 0h3a1.5 1.5 0 010 3h-3A1.5 1.5 0 015 1.5zM6.5 1a.5.5 0 000 1h3a.5.5 0 000-1h-3z"/>
|
||||
<path fill="@image.color2" d="M8 9.5A1.5 1.5 0 019.5 8h5A1.5 1.5 0 0116 9.5v5a1.5 1.5 0 01-1.5 1.5h-5A1.5 1.5 0 018 14.5v-5z"/>
|
||||
<path fill="@color_islight_WB" d="M10.5 10a.5.5 0 000 1h1.61l-2.05 2.05a.62.62 0 10.88.88L13 11.88V13.5a.5.5 0 001 0v-3a.5.5 0 00-.5-.5h-3z"/>
|
||||
</svg>'
|
||||
|
||||
@move_to, move_here='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M2.5 1.5h3a2 2 0 011.6.8L8 3.5h4.5a2 2 0 012 2 .87.87 0 01.86.99l-.09.66A5.75 5.75 0 006.59 14.5H2.5a2 2 0 01-2-2v-9a2 2 0 012-2z"/>
|
||||
<path fill="@image.color1" d="M2.5 1A2.5 2.5 0 000 3.5v9A2.5 2.5 0 002.5 15h4.43a5.75 5.75 0 01-.61-1H2.5c-.25 0-.49-.06-.70-.17l1.44-7.02A1 1 0 014.22 6h5.59a5.75 5.75 0 011.68-.25c.58 0 1.15.08 1.68.25h.59a1 1 0 01.97.75c.35.24.67.52.96.83l.04-.31a1.99 1.99 0 00-.76-1.86A2.5 2.5 0 0012.5 3H8.25L7.5 2a2.5 2.5 0 00-2-1h-3zm10 3a1.5 1.5 0 011.41 1.00A2.04 2.04 0 0013.77 5H4.22a2 2 0 00-1.96 1.59l-1.25 6.08c-.00-.06-.01-.12-.01-.18v-9A1.5 1.5 0 012.5 2h3a1.5 1.5 0 011.2.6l.9 1.2.15.2h4.75z"/>
|
||||
<path fill="@image.color2" d="M11.5 7a4.5 4.5 0 110 9 4.5 4.5 0 010-9z"/>
|
||||
<path fill="#fff" d="M11.14 13.85a.5.5 0 010-.70l1.64-1.64-1.64-1.64a.5.5 0 01.70-.70l2 2a.5.5 0 010 .70l-2 2a.5.5 0 01-.70 0z"/>
|
||||
<path fill="#fff" d="M9 11.5a.5.5 0 01.5-.5h4a.5.5 0 010 1h-4a.5.5 0 01-.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@copy_as_path, copy_path='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g>
|
||||
<path fill="@color3" d="M13 2.5H3A2.5 2.5 0 00.5 5v6A2.5 2.5 0 003 13.5h10a2.5 2.5 0 002.5-2.5V5A2.5 2.5 0 0013 2.5z"/>
|
||||
<path fill="@image.color1" d="M0 5a3 3 0 013-3h10a3 3 0 013 3v6a3 3 0 01-3 3H3a3 3 0 01-3-3V5zm3-2a2 2 0 00-2 2v6a2 2 0 002 2h10a2 2 0 002-2V5a2 2 0 00-2-2H3z"/>
|
||||
<path fill="@image.color2" d="M2.36 4.02a.5.5 0 01.61.34l2 7a.5.5 0 01-.96.27l-2-7a.5.5 0 01.34-.61zm3 0a.5.5 0 01.61.34l2 7a.5.5 0 01-.96.27l-2-7a.5.5 0 01.34-.61zM11 11.25a.75.75 0 11-1.5 0 .75.75 0 011.5 0zM13.5 11.25a.75.75 0 11-1.5 0 .75.75 0 011.5 0z"/>
|
||||
</g>
|
||||
</svg>'
|
||||
|
||||
@settings, options, folder_options, taskbar_settings='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@image.color1" d="M8.00 16c-.43 0-.87-.03-1.3-.10a1 1 0 01-.81-.82l-.26-1.51a.93.93 0 00-.45-.63.94.94 0 00-.38-.12.90.90 0 00-.4.05l-1.47.52a1 1 0 01-1.11-.30 8.21 8.21 0 01-1.28-2.24 1.00 1.00 0 01.3-1.12l1.18-.98a.94.94 0 000-1.43L.80 6.27a1 1 0 01-.29-1.12 8.21 8.21 0 011.30-2.22 1.00 1.00 0 011.12-.3l1.44.53a.91.91 0 00.4.05.96.96 0 00.38-.12.93.93 0 00.45-.64L5.89.90A1 1 0 016.73.09c.42-.06.84-.09 1.26-.09.43-.00.87.03 1.3.1.20.03.39.13.54.28a.97.97 0 01.27.53l.26 1.52a.95.95 0 00.84.76.95.95 0 00.4-.05l1.47-.52a1 1 0 011.11.30 8.18 8.18 0 011.27 2.24 1.00 1.00 0 01-.30 1.12l-1.17.98a.93.93 0 00-.33.71.93.93 0 00.33.72l1.18 1a1 1 0 01.29 1.12 8.17 8.17 0 01-1.31 2.22 1.01 1.01 0 01-1.11.3 52.11 52.11 0 01-.97-.36 2.01 2.01 0 00-.78-.22.94.94 0 00-.88.62c-.02.07-.06.3-.17.89l-.14.79a1 1 0 01-.83.81A9.22 9.22 0 018.00 16zm-3.30-4.21a1.98 1.98 0 01.97.25 1.94 1.94 0 01.94 1.33l.26 1.52c.74.12 1.51.12 2.26.01l.13-.79a7.54 7.54 0 01.21-1.04 1.94 1.94 0 011.82-1.28 2.86 2.86 0 011.13.29c.23.08.53.2.95.35.49-.58.88-1.23 1.15-1.94h-.00L13.36 9.48a1.94 1.94 0 01-.50-2.29 1.9 1.9 0 01.50-.66l1.18-.98a6.98 6.98 0 00-1.11-1.96l-1.47.53A1.94 1.94 0 019.4 2.62l-.26-1.52A6.67 6.67 0 008.00 1a8.13 8.13 0 00-1.12.08l-.27 1.53A1.94 1.94 0 014.04 4.09l-1.44-.53a7.01 7.01 0 00-1.15 1.94l1.2 1.01a1.94 1.94 0 01.50 2.29 1.93 1.93 0 01-.5.66l-1.18.98a7.02 7.02 0 001.11 1.96l1.47-.53a1.95 1.95 0 01.65-.11z"/>
|
||||
<path stroke="@image.color2" stroke-linejoin="round" d="M8 10.5a2.5 2.5 0 110-5 2.5 2.5 0 010 5z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@task_manager='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M3.9 15C3.6 15 3.2 15 2.8 15C2.8 15 2.5 15 2.1 14C2.1 14 1.9 14 1.6 14C1.6 14 1.4 14 1.2 13C1.2 13 1.1 13 1 12L1 3.9C1 3.5 1.1 3.2 1.2 2.8C1.2 2.8 1.4 2.5 1.6 2.1C1.6 2.1 1.9 1.9 2.1 1.6C2.1 1.6 2.5 1.4 2.8 1.2C2.8 1.2 3.2 1.1 3.6 1L12 1C12 1 13 1.1 13 1.2C13 1.2 14 1.4 14 1.6C14 1.6 14 1.9 14 2.1C14 2.1 15 2.5 15 2.8C15 2.8 15 3.2 15 3.5L15 12C15 12 15 13 15 13C15 13 15 14 14 14C14 14 14 14 14 14C14 14 14 15 13 15C13 15 13 15 12 15ZM12 14C12 14 13 14 13 14C13 14 13 14 13 14C13 14 13 13 14 13C14 13 14 13 14 13C14 13 14 13 14 12L14 4C14 3.7 14 3.5 14 3.2C14 3.2 14 3 14 2.8C14 2.8 13 2.6 13 2.4C13 2.4 13 2.3 13 2.2C13 2.2 13 2 12 2L4 2C3.7 2 3.5 2 3.2 2.2C3.2 2.2 3 2.3 2.8 2.4C2.8 2.4 2.6 2.6 2.4 2.8C2.4 2.8 2.3 3 2.2 3.2C2.2 3.2 2 3.5 2 3.7L2 12C2 12 2 13 2.2 13C2.2 13 2.3 13 2.4 13C2.4 13 2.6 13 2.8 14C2.8 14 3 14 3.2 14C3.2 14 3.5 14 3.7 14Z"/>
|
||||
<path fill="@image.color2" d="M9 12C8.9 12 8.8 12 8.7 12C8.7 12 8.6 12 8.6 12L6.9 6.1L6 8.7C5.9 8.8 5.9 8.8 5.8 8.9C5.8 8.9 5.7 9 5.6 9L3.5 9C3.4 9 3.2 9 3.1 8.8C3.1 8.8 3.1 8.8 3 8.6C3 8.4 3.1 8.2 3.1 8.2C3.1 8.2 3.2 8.1 3.4 8L5.2 8L6.5 4.3C6.6 4.2 6.6 4.1 6.7 4.1C6.7 4.1 6.8 4 6.9 4C7.1 4 7.2 4 7.3 4.1C7.3 4.1 7.4 4.2 7.5 4.3L9.1 10L10 8.3C10 8.2 10 8.1 10 8.1C10 8.1 10 8 10 8L12 8C13 8 13 8.1 13 8.2C13 8.2 13 8.2 13 8.4C13 8.6 13 8.8 13 8.8C13 8.8 13 9 13 9L11 9L9.5 12C9.4 12 9.3 12 9.2 12C9.2 12 9.2 12 9.1 12Z"/>
|
||||
</svg>'
|
||||
|
||||
@run_as_administrator='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M1.5 4v8A2.5 2.5 0 004 14.5h4.13c-.77-1.15-.99-2.49-1.12-3.81L7 8.08a1.41 1.41 0 011.4-1.41 3.52 3.52 0 002.59-1.23 1.38 1.38 0 012.00 0A3.51 3.51 0 0014.5 6.46V4A2.5 2.5 0 0012 1.5H4A2.5 2.5 0 001.5 4z"/>
|
||||
<path fill="@image.color1" d="M2 12V5h12v1.23a3.48 3.48 0 001 .36V4a3 3 0 00-3-3H4a3 3 0 00-3 3v8a3 3 0 003 3h4.51a5.21 5.21 0 01-.67-1H4a2 2 0 01-2-2zM4 2h8a2 2 0 012 2H2a2 2 0 012-2z"/>
|
||||
<path fill="@image.color2" d="M15.6 7.66a.40.40 0 01.39.33L16 10.58a5.29 5.29 0 01-3.87 5.39.38.38 0 01-.25 0C8.81 14.91 8.24 13.05 8 10.58V8.08a.40.40 0 01.4-.41 4.49 4.49 0 003.31-1.54.38.38 0 01.56 0A4.50 4.50 0 0015.6 7.66z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@run_as_different_user, run_as_another_user='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M6.9 14C7 14 7.2 15 7.4 15L3.9 15C3.6 15 3.2 15 2.8 15C2.8 15 2.5 15 2.1 14C2.1 14 1.9 14 1.6 14C1.6 14 1.4 14 1.2 13C1.2 13 1.1 13 1 12L1 3.9C1 3.5 1.1 3.2 1.2 2.8C1.2 2.8 1.4 2.5 1.6 2.1C1.6 2.1 1.9 1.9 2.1 1.6C2.1 1.6 2.5 1.4 2.8 1.2C2.8 1.2 3.2 1.1 3.6 1L12 1C12 1 13 1.1 13 1.2C13 1.2 14 1.4 14 1.6C14 1.6 14 1.9 14 2.1C14 2.1 15 2.5 15 2.8C15 2.8 15 3.2 15 3.5L15 5.2C15 5.1 15 4.9 15 4.8C15 4.8 14 4.6 14 4.5L14 4C14 3.7 14 3.5 14 3.2C14 3.2 14 3 14 2.8C14 2.8 13 2.6 13 2.4C13 2.4 13 2.3 13 2.2C13 2.2 13 2 12 2L4 2C3.7 2 3.4 2 3.2 2.2C3.2 2.2 3 2.3 2.8 2.4C2.8 2.4 2.6 2.6 2.4 2.8C2.4 2.8 2.3 3 2.2 3.2C2.2 3.2 2 3.5 2 3.7L11 4C10 4.2 9.6 4.5 9.2 5L2 5L2 12C2 12 2 13 2.2 13C2.2 13 2.3 13 2.4 13C2.4 13 2.6 13 2.8 14C2.8 14 3 14 3.2 14C3.2 14 3.5 14 3.7 14Z"/>
|
||||
<path fill="@image.color2" d="M14 7.5C14 7.9 14 8.2 14 8.5C14 8.5 14 8.8 14 9.1C14 9.1 14 9.3 14 9.5C14 9.5 13 9.7 13 9.8C13 9.8 13 9.9 12 10C12 10 11 9.9 11 9.8C11 9.8 11 9.7 10 9.5C10 9.5 10 9.3 10 9C10 9 9.8 8.8 9.7 8.5C9.7 8.5 9.6 8.2 9.5 7.8C9.5 7.2 9.6 6.8 9.7 6.5C9.7 6.5 9.8 6.2 10 6C10 6 10 5.7 10 5.5C10 5.5 11 5.3 11 5.2C11 5.2 11 5.1 12 5C12 5 13 5.1 13 5.2C13 5.2 13 5.3 14 5.5C14 5.5 14 5.7 14 6C14 6 14 6.2 14 6.5C14 6.5 14 6.9 14 7.2Z"/>
|
||||
<path fill="@image.color2" d="M16 13C16 13 16 14 16 14C16 14 16 14 16 14C16 14 15 15 15 15C15 15 15 15 15 15C15 15 14 15 14 16C14 16 14 16 14 16C14 16 13 16 13 16C13 16 13 16 12 16C12 16 11 16 11 16C11 16 11 16 11 16C11 16 10 16 9.9 16C9.9 16 9.7 15 9.4 15C9.4 15 9.1 15 8.9 15C8.9 15 8.7 15 8.5 14C8.5 14 8.3 14 8.2 14C8.2 14 8.1 14 8 13L8 13C8 12 8 12 8.1 12C8.1 12 8.2 12 8.3 12C8.3 12 8.5 11 8.6 11C8.6 11 8.8 11 9 11C9 11 9.2 11 9.4 11L14 11C15 11 15 11 15 11C15 11 15 11 15 11C15 11 16 11 16 12C16 12 16 12 16 12C16 12 16 12 16 12Z"/>
|
||||
</svg>'
|
||||
|
||||
@personalize='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M15.17.76c.40.37.41.87.06 1.41l-1.32 1.94a47.29 47.29 0 01-7.33 8.40l-2.27-2.11a46.41 46.41 0 017.91-8.32L13.76.82C14.2.45 14.76.39 15.17.76z"/>
|
||||
<path fill="@image.color1" d="M13.44.44c.56-.47 1.42-.64 2.06-.05.29.26.46.61.48.99.01.37-.12.73-.32 1.05l-.00.01-1.32 1.93a47.79 47.79 0 01-7.40 8.49l-.67-.74a46.79 46.79 0 007.25-8.31l1.32-1.93c.13-.20.17-.36.16-.47-.00-.09-.03-.19-.15-.29-.16-.15-.44-.18-.75.08l-.00.00-1.53 1.25a45.91 45.91 0 00-7.83 8.22l-.80-.59a46.91 46.91 0 018-8.40L13.44.44z"/>
|
||||
<path fill="@color3" d="M2.49 15.5c-.62 0-1.60-.15-1.99-.28 1.32-1.11 1.68-1.18 1.85-2.56 0-1.75 1.47-2.16 2.21-2.15.69.04 1.92.57 1.92 2.30 0 2.16-2.84 2.69-4.00 2.69z"/>
|
||||
<path fill="@image.color2" d="M2.90 10.50A2.96 2.96 0 014.60 10c.43.03 1.03.20 1.52.64.50.45.87 1.16.87 2.15 0 1.35-.91 2.16-1.85 2.61-.94.44-2.01.58-2.65.58-.67 0-1.70-.16-2.14-.30a.5.5 0 01-.17-.85c.2-.16.39-.32.55-.45l.27-.22c.21-.18.36-.31.47-.44.18-.22.29-.47.38-1.09.01-1.02.45-1.70 1.04-2.11zm.57.82c-.33.22-.61.61-.61 1.32a.50.50 0 01-.00.06c-.09.73-.24 1.20-.61 1.64a4.64 4.64 0 01-.60.57c.3.04.61.06.86.06.52 0 1.45-.12 2.22-.48.76-.36 1.28-.89 1.28-1.70 0-.73-.25-1.16-.53-1.41A1.61 1.61 0 004.55 11a1.96 1.96 0 00-1.07.32z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@display_settings='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M2 .5h12A1.5 1.5 0 0115.5 2v5.72A5.5 5.5 0 006.09 12.5H2A1.5 1.5 0 01.5 11V2A1.5 1.5 0 012 .5z"/>
|
||||
<path fill="@image.color1" d="M14 1H2a1 1 0 00-1 1v9a1 1 0 001 1h4.02c.03.34.09.67.18 1H6v2h1.25c.31.38.67.71 1.08 1H3.5a.5.5 0 010-1H5v-2H2a2 2 0 01-2-2V2a2 2 0 012-2h12a2 2 0 012 2v6.33a5.53 5.53 0 00-1-1.08V2a1 1 0 00-1-1z"/>
|
||||
<path fill="@image.color2" d="M10.07 15.13l-.35.35a4.53 4.53 0 01-.87-.48l.11-.39a2 2 0 00-1.45-2.52l-.48-.11a4.25 4.25 0 010-.96l.48-.11a2 2 0 001.45-2.52l-.11-.39c.27-.19.56-.35.87-.48l.35.35a2 2 0 002.86 0l.35-.35c.31.13.60.29.87.48l-.11.39a2 2 0 001.45 2.52l.48.11a4.25 4.25 0 010 .96l-.48.11a2 2 0 00-1.45 2.52l.11.39c-.27.19-.56.35-.87.48l-.35-.35a2 2 0 00-2.86 0zM11.5 10.5a1 1 0 100 2 1 1 0 000-2z"/>
|
||||
</svg>'
|
||||
|
||||
// pin
|
||||
@pin, pin_to_start, pin_to_taskbar, pin_to_quick_access, pin_current_folder_to_quick_access, pin_to_start_menu='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M5.27 11.43L.70 16l-.00-.00H.00v-.70L0 15.29l4.56-4.56.70.70z"/>
|
||||
<path fill="@color3" d="M8.40 1.31l-1.73 3.82a1 1 0 01-.53.51L1.5 7.5l7 7 1.36-4.54a1 1 0 01.57-.63l4.18-1.74a1 1 0 00.32-1.63L10.02 1.02a1 1 0 00-1.61.29z"/>
|
||||
<path fill="@image.color2" fill-rule="evenodd" d="M9.04.25a1.5 1.5 0 011.32.41l4.92 4.92a1.50 1.50 0 01-.48 2.44l-4.18 1.74a.5.5 0 00-.28.31l-1.36 4.54a.5.5 0 01-.83.21l-7-7a.5.5 0 01.16-.81l4.62-1.85a.5.5 0 00.27-.25m0 0l1.73-3.82A1.5 1.5 0 019.04.25m.41.99a.5.5 0 00-.60.27L7.12 5.34c-.16.35-.45.62-.80.77L2.39 7.68l5.87 5.87L9.38 9.81a1.5 1.5 0 01.86-.95l4.18-1.74a.5.5 0 00.16-.81L9.66 1.37" clip-rule="evenodd"/>
|
||||
</svg>'
|
||||
|
||||
// unpin
|
||||
@unpin, unpin_from_start, unpin_from_taskbar, unpin_from_quick_access, remove_from_quick_access, remove_from_recent, unpin_from_start_menu='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@image.color1" d="M5.27 11.43L.70 16l-.00-.00H.00v-.70L0 15.29l4.56-4.56.70.70z"/>
|
||||
<path fill="@color3" d="M5.28 5.98L1.5 7.5l7 7 1.22-4.07-4.44-4.44zM11.14 9.02l3.47-1.44a1 1 0 00.32-1.63L10.02 1.02a1 1 0 00-1.61.29L6.85 4.72l4.29 4.29zM5.78 5.78l4.1 4.1a1 1 0 01.29-.41L6.28 5.57a1 1 0 01-.15.07l-.34.13z"/>
|
||||
<g>
|
||||
<path fill="@image.color1" d="M4.89 5.60L1.31 7.03a.5.5 0 00-.16.81l7 7a.5.5 0 00.83-.21l1.14-3.81-.80-.80-1.05 3.52L2.39 7.68l3.27-1.31-.77-.77zM9.51 9.51l.77.77.05-.18a.5.5 0 01.19-.26l-.71-.71a1.5 1.5 0 00-.31.39zM6.64 5.93a1.5 1.5 0 01-.32.18l-.14.05-.76-.76.50-.20.73.73zM10.76 8.64l3.66-1.52a.5.5 0 00.16-.81L9.66 1.37l-.20-.12a.5.5 0 00-.60.27l-1.63 3.58-.75-.75 1.47-3.24a1.5 1.5 0 012.42-.44l4.92 4.92a1.50 1.50 0 01-.48 2.44l-3.28 1.37-.76-.76z"/>
|
||||
</g>
|
||||
<path fill="@image.color2" d="M.14.14a.5.5 0 01.70 0l15 15a.5.5 0 01-.70.70l-15-15a.5.5 0 010-.70z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@add_to_favorites='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M10.3 5.6L8 .9 5.7 5.6l-5.2.7L4.25 10l-.86 5.10L8 12.68l4.60 2.42-.86-5.10L15.5 6.3l-5.2-.7z"/>
|
||||
<path fill="@image.color2" d="M8 2.01l1.74 3.54.23.47.52.07 3.91.56-2.83 2.75-.37.36.08.51.66 3.89-3.49-1.83L8 12.12l-.46.24-3.49 1.83.66-3.89.08-.51-.37-.36L1.59 6.66 5.5 6.1l.52-.07.23-.47L8 2.01zM7.99.38a.49.49 0 00-.44.27l-2.19 4.45-4.91.71a.5.5 0 00-.27.85l3.55 3.46-.83 4.89a.50.50 0 00.49.58c.08 0 .16-.02.23-.05L8 13.25l4.39 2.31a.49.49 0 00.61-.12.50.50 0 00.11-.40l-.84-4.89 3.55-3.46a.5.5 0 00-.27-.85l-4.91-.71L8.44.65a.49.49 0 00-.45-.27z"/>
|
||||
</svg>'
|
||||
|
||||
@remove_from_favorites='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M4.98 5.69L.5 6.3 4.25 10l-.86 5.10L8 12.68l4.60 2.42-.36-2.15-7.25-7.25zM11.93 9.81L15.5 6.3l-5.2-.7L8 .9 6.36 4.24l5.57 5.57zM5.61 5.61l6.49 6.49-.14-.85-6.06-6.06L5.7 5.6l-.08.01z"/>
|
||||
<g>
|
||||
<path fill="@image.color1" d="M4.52 5.23l-4.08.59a.5.5 0 00-.27.85l3.55 3.46-.83 4.89a.50.50 0 00.49.58c.08 0 .16-.02.23-.05L8 13.25l4.39 2.31a.49.49 0 00.61-.12.50.50 0 00.11-.40l-.25-1.45-1.22-1.22.31 1.85L8 12.12l-3.96 2.08.75-4.41-3.20-3.12 3.81-.55-.88-.88zM11.49 11.49l1.22 1.22-.14-.85-1.22-1.22.14.85zM6.25 5.54l-.23.47-.88-.88.21-.03.15-.31.74.74zM11.56 9.44l2.84-2.77-4.43-.64L8 2.01 6.72 4.6l-.74-.74L7.55.65A.49.49 0 017.99.38a.49.49 0 01.45.27l2.19 4.45 4.91.71a.5.5 0 01.27.85l-3.55 3.46.00.02-.72-.71z"/>
|
||||
</g>
|
||||
<path fill="@image.color2" d="M.14.14a.5.5 0 01.70 0l15 15a.5.5 0 01-.70.70l-15-15a.5.5 0 010-.70z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@delete, permanently_delete, empty_recycle_bin='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M14 2.5H2l1.34 11.67a1.5 1.5 0 001.49 1.32h6.32a1.5 1.5 0 001.49-1.32L14 2.5z"/>
|
||||
<path fill="@image.color1" d="M15 2a.5.5 0 010 1h-.55L13.15 14.23A2 2 0 0111.16 16H4.83a2 2 0 01-1.98-1.77L1.55 3H1a.5.5 0 01-.49-.41L.5 2.5A.5.5 0 011 2h14zm-1.56 1H2.56l1.28 11.11a1 1 0 00.99.88h6.32a1 1 0 00.99-.88L13.43 3z"/>
|
||||
<path fill="@image.color2" d="M8 1a1.5 1.5 0 00-1.5 1.5h-1a2.5 2.5 0 015 0h-1A1.5 1.5 0 008 1zM6.5 6a.5.5 0 01.5.5v5a.5.5 0 01-1 0v-5a.5.5 0 01.5-.5zM9.5 6a.5.5 0 01.5.5v5a.5.5 0 01-1 0v-5a.5.5 0 01.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@sort_by='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@image.color2" fill-rule="evenodd" d="M11.5 2a.5.5 0 01.5.5v11a.5.5 0 01-1 0v-11a.5.5 0 01.5-.5z" clip-rule="evenodd"/>
|
||||
<path fill="@image.color2" fill-rule="evenodd" d="M7.14 9.14a.5.5 0 01.70 0l3.64 3.64 3.64-3.64a.5.5 0 01.70.70l-4 4a.5.5 0 01-.70 0l-4-4a.5.5 0 010-.70z" clip-rule="evenodd"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M4.5 2a.5.5 0 01.5.5v11a.5.5 0 01-1 0v-11a.5.5 0 01.5-.5z" clip-rule="evenodd"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M4.14 2.14a.5.5 0 01.70 0l4 4a.5.5 0 11-.70.70L4.5 3.20.85 6.85a.5.5 0 11-.70-.70l4-4z" clip-rule="evenodd"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@group_by='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M5 2.5a.5.5 0 01.5-.5h9a.5.5 0 010 1h-9a.5.5 0 01-.5-.5zm0 3a.5.5 0 01.5-.5h9a.5.5 0 010 1h-9a.5.5 0 01-.5-.5zm0 5a.5.5 0 01.5-.5h9a.5.5 0 010 1h-9a.5.5 0 01-.5-.5zm0 3a.5.5 0 01.5-.5h9a.5.5 0 010 1h-9a.5.5 0 01-.5-.5z"/>
|
||||
<path fill="@image.color2" d="M1 2.5A1.5 1.5 0 012.5 1h1a.5.5 0 010 1h-1a.5.5 0 00-.5.5v3a.5.5 0 00.5.5h1a.5.5 0 010 1h-1A1.5 1.5 0 011 5.5v-3zm0 8A1.5 1.5 0 012.5 9h1a.5.5 0 010 1h-1a.5.5 0 00-.5.5v3a.5.5 0 00.5.5h1a.5.5 0 010 1h-1A1.5 1.5 0 011 13.5v-3z"/>
|
||||
</svg>'
|
||||
|
||||
@view='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M1.5 3A1.5 1.5 0 013 1.5h2A1.5 1.5 0 016.5 3v2A1.5 1.5 0 015 6.5H3A1.5 1.5 0 011.5 5V3z"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M1 3a2 2 0 012-2h2a2 2 0 012 2v2a2 2 0 01-2 2H3a2 2 0 01-2-2V3zm2-1a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1V3a1 1 0 00-1-1H3z" clip-rule="evenodd"/>
|
||||
<path fill="@color3" d="M9.5 3A1.5 1.5 0 0111 1.5h2A1.5 1.5 0 0114.5 3v2A1.5 1.5 0 0113 6.5h-2A1.5 1.5 0 019.5 5V3z"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M9 3a2 2 0 012-2h2a2 2 0 012 2v2a2 2 0 01-2 2h-2a2 2 0 01-2-2V3zm2-1a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1V3a1 1 0 00-1-1h-2z" clip-rule="evenodd"/>
|
||||
<path fill="@color3" d="M1.5 11A1.5 1.5 0 013 9.5h2A1.5 1.5 0 016.5 11v2A1.5 1.5 0 015 14.5H3A1.5 1.5 0 011.5 13v-2z"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M1 11a2 2 0 012-2h2a2 2 0 012 2v2a2 2 0 01-2 2H3a2 2 0 01-2-2v-2zm2-1a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1H3z" clip-rule="evenodd"/>
|
||||
<path fill="@color3" d="M9.5 11A1.5 1.5 0 0111 9.5h2a1.5 1.5 0 011.5 1.5v2a1.5 1.5 0 01-1.5 1.5h-2A1.5 1.5 0 019.5 13v-2z"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M9 11a2 2 0 012-2h2a2 2 0 012 2v2a2 2 0 01-2 2h-2a2 2 0 01-2-2v-2zm2-1a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1h-2z" clip-rule="evenodd"/>
|
||||
</svg>'
|
||||
|
||||
@view2='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M0.2344 9.516C0.2344 9.484 0.2396 9.443 0.25 9.391C0.4167 8.787 0.6302 8.208 0.8906 7.656C0.8906 7.656 1.151 7.104 1.461 6.591C1.461 6.591 1.82 6.117 2.18 5.643C2.18 5.643 2.583 5.214 3.031 4.828C3.031 4.828 3.479 4.443 3.964 4.115C3.964 4.115 4.484 3.844 5.005 3.573C5.005 3.573 5.56 3.365 6.148 3.219C6.148 3.219 6.737 3.073 7.354 3C8.75 3 9.474 3.107 10.17 3.32C10.17 3.32 10.87 3.534 11.52 3.833C11.52 3.833 12.12 4.219 12.73 4.604C12.73 4.604 13.28 5.065 13.77 5.602C13.77 5.602 14.27 6.138 14.69 6.734C15.08 7.495 15.15 7.643 15.23 7.836C15.23 7.836 15.32 8.029 15.4 8.232C15.4 8.232 15.48 8.445 15.55 8.659C15.55 8.659 15.62 8.862 15.68 9.055C15.68 9.055 15.74 9.247 15.77 9.396C15.77 9.635 15.72 9.753 15.62 9.852C15.62 9.852 15.52 9.95 15.4 10C15.13 10 15.03 9.963 14.96 9.891C14.96 9.891 14.89 9.818 14.83 9.724C14.73 9.495 14.69 9.372 14.66 9.242C14.66 9.242 14.64 9.112 14.6 8.984C14.44 8.474 14.27 8.096 14.07 7.727C14.07 7.727 13.87 7.357 13.64 7.016C13.06 6.276 12.69 5.896 12.28 5.562C12.28 5.562 11.88 5.229 11.44 4.945C11.44 4.945 10.98 4.711 10.51 4.477C10.51 4.477 10.03 4.3 9.516 4.18C9.516 4.18 9.005 4.06 8.474 4C7.276 4 6.654 4.096 6.055 4.289C6.055 4.289 5.456 4.482 4.896 4.747C4.896 4.747 4.375 5.086 3.854 5.425C3.854 5.425 3.38 5.831 2.953 6.305C2.953 6.305 2.526 6.779 2.167 7.292C1.833 7.917 1.781 8.021 1.719 8.156C1.719 8.156 1.656 8.292 1.594 8.435C1.594 8.435 1.531 8.586 1.469 8.737C1.469 8.737 1.417 8.88 1.375 9.016C1.375 9.016 1.333 9.151 1.312 9.25C1.312 9.396 1.297 9.477 1.266 9.555C1.266 9.555 1.234 9.633 1.195 9.706C1.195 9.706 1.148 9.773 1.102 9.841C1.102 9.841 1.042 9.896 0.9688 9.938C0.9688 9.938 0.8958 9.979 0.8177 10C0.599 10 0.4818 9.953 0.3828 9.859C0.3828 9.859 0.2839 9.766 0.2344 9.651Z"/>
|
||||
<path fill="@image.color2" d="M4.5 9.438C4.5 8.969 4.596 8.526 4.789 8.109C4.789 8.109 4.982 7.693 5.237 7.328C5.237 7.328 5.555 7.016 5.872 6.703C5.872 6.703 6.242 6.456 6.664 6.273C6.664 6.273 7.086 6.091 7.531 6C8.479 6 8.932 6.091 9.359 6.273C9.359 6.273 9.787 6.456 10.16 6.706C10.16 6.706 10.48 7.023 10.79 7.341C10.79 7.341 11.04 7.714 11.23 8.141C11.23 8.141 11.41 8.568 11.5 9.021C11.5 9.979 11.41 10.43 11.23 10.85C11.23 10.85 11.04 11.27 10.79 11.64C10.79 11.64 10.48 11.96 10.16 12.28C10.16 12.28 9.787 12.53 9.359 12.72C9.359 12.72 8.932 12.91 8.479 13C7.51 13 7.052 12.91 6.625 12.72C6.625 12.72 6.198 12.53 5.828 12.28C5.828 12.28 5.516 11.95 5.203 11.63C5.203 11.63 4.956 11.25 4.773 10.82C4.773 10.82 4.591 10.39 4.5 9.927ZM10.5 9.438C10.5 9.104 10.43 8.789 10.3 8.492C10.3 8.492 10.16 8.195 9.979 7.935C9.979 7.935 9.75 7.711 9.521 7.487C9.521 7.487 9.255 7.312 8.953 7.188C8.953 7.188 8.651 7.062 8.333 7C7.656 7 7.333 7.065 7.031 7.195C7.031 7.195 6.729 7.326 6.464 7.503C6.464 7.503 6.234 7.727 6.005 7.951C6.005 7.951 5.825 8.213 5.695 8.516C5.695 8.516 5.565 8.818 5.5 9.146C5.5 9.844 5.565 10.17 5.695 10.47C5.695 10.47 5.825 10.77 6.005 11.04C6.005 11.04 6.234 11.27 6.464 11.49C6.464 11.49 6.729 11.67 7.031 11.8C7.031 11.8 7.333 11.93 7.656 12C8.365 12 8.698 11.93 9 11.8C9 11.8 9.302 11.66 9.565 11.48C9.565 11.48 9.789 11.25 10.01 11.02C10.01 11.02 10.19 10.75 10.31 10.44C10.31 10.44 10.44 10.12 10.5 9.792Z"/>
|
||||
</svg>'
|
||||
|
||||
@align_icons_to_grid='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color2" d="M2.5 0a.5.5 0 01.5.5V2h12.5a.5.5 0 010 1H3v12.5a.5.5 0 01-1 0V3H.5a.5.5 0 010-1H2V.5a.5.5 0 01.5-.5z"/>
|
||||
<path fill="@color3" d="M4.5 12.5v-7a1 1 0 011-1h7a1 1 0 011 1v7a1 1 0 01-1 1h-7a1 1 0 01-1-1z"/>
|
||||
<path fill="@image.color1" d="M5.5 5a.5.5 0 00-.5.5v7a.5.5 0 00.5.5h7a.5.5 0 00.5-.5v-7a.5.5 0 00-.5-.5h-7zM4 5.5A1.5 1.5 0 015.5 4h7A1.5 1.5 0 0114 5.5v7a1.5 1.5 0 01-1.5 1.5h-7A1.5 1.5 0 014 12.5v-7z"/>
|
||||
</svg>'
|
||||
|
||||
@auto_arrange_icons='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color2" d="M6.5 10H4.75a.5.5 0 01-.46-.69l2.08-5A.5.5 0 016.83 4h3.47a.5.5 0 01.47.65L10 7h1.09a.75.75 0 01.51 1.29l-4.87 4.54c-.36.34-.94-.00-.82-.48L6.5 10z"/>
|
||||
<path fill="@image.color1" d="M1.5 0a.5.5 0 01.5.5V1h12V.5a.5.5 0 011 0V1h.5a.5.5 0 010 1H15v12h.5a.5.5 0 010 1H15v.5a.5.5 0 01-1 0V15H2v.5a.5.5 0 01-1 0V15H.5a.5.5 0 010-1H1V2H.5a.5.5 0 010-1H1V.5a.5.5 0 01.5-.5zM2 2v12h12V2H2z"/>
|
||||
</svg>'
|
||||
|
||||
@close, cancel='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color2" d="M1.85 1.14a.5.5 0 10-.70.70L7.29 8l-6.14 6.14a.5.5 0 00.70.70L8 8.70l6.14 6.14a.5.5 0 00.70-.70L8.70 8l6.14-6.14a.5.5 0 00-.70-.70L8 7.29 1.85 1.14z"/>
|
||||
</svg>'
|
||||
|
||||
@expand='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M11 1.5H4A2.5 2.5 0 001.5 4v7A2.5 2.5 0 004 13.5h7a2.5 2.5 0 002.5-2.5V4A2.5 2.5 0 0011 1.5z"/>
|
||||
<path fill="@image.color1" d="M1 4a3 3 0 013-3h7a3 3 0 013 3v7a3 3 0 01-3 3H4a3 3 0 01-3-3V4zm3-2a2 2 0 00-2 2v7a2 2 0 002 2h7a2 2 0 002-2V4a2 2 0 00-2-2H4z"/>
|
||||
<path fill="@image.color2" d="M7.5 4a.5.5 0 01.5.5V7h2.5a.5.5 0 010 1H8v2.5a.5.5 0 01-1 0V8H4.5a.5.5 0 010-1H7V4.5a.5.5 0 01.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@expand_all, expand_group, expand_all_groups='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M11 1.5H4A2.5 2.5 0 001.5 4v7A2.5 2.5 0 004 13.5h7a2.5 2.5 0 002.5-2.5V4A2.5 2.5 0 0011 1.5z"/>
|
||||
<path fill="@image.color1" d="M3.76 15c.54.61 1.34 1 2.23 1h6a4 4 0 004-4V6c0-.88-.38-1.68-1-2.23V12a3 3 0 01-3 3H3.76z"/>
|
||||
<path fill="@image.color1" d="M1 4a3 3 0 013-3h7a3 3 0 013 3v7a3 3 0 01-3 3H4a3 3 0 01-3-3V4zm3-2a2 2 0 00-2 2v7a2 2 0 002 2h7a2 2 0 002-2V4a2 2 0 00-2-2H4z"/>
|
||||
<path fill="@image.color2" d="M7.5 4a.5.5 0 01.5.5V7h2.5a.5.5 0 010 1H8v2.5a.5.5 0 01-1 0V8H4.5a.5.5 0 010-1H7V4.5a.5.5 0 01.5-.5z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@collapse='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M11 1.5H4A2.5 2.5 0 001.5 4v7A2.5 2.5 0 004 13.5h7a2.5 2.5 0 002.5-2.5V4A2.5 2.5 0 0011 1.5z"/>
|
||||
<path fill="@image.color1" d="M1 4a3 3 0 013-3h7a3 3 0 013 3v7a3 3 0 01-3 3H4a3 3 0 01-3-3V4zm3-2a2 2 0 00-2 2v7a2 2 0 002 2h7a2 2 0 002-2V4a2 2 0 00-2-2H4z"/>
|
||||
<path fill="@image.color2" d="M4 7.5a.5.5 0 01.5-.5h6a.5.5 0 010 1h-6a.5.5 0 01-.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@collapse_all, collapse_group, collapse_all_groups='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M11 1.5H4A2.5 2.5 0 001.5 4v7A2.5 2.5 0 004 13.5h7a2.5 2.5 0 002.5-2.5V4A2.5 2.5 0 0011 1.5z"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M3.76 15c.55.61 1.34 1 2.23 1h6a4 4 0 004-4V6c0-.88-.38-1.68-1-2.23V12a3 3 0 01-3 3H3.76z" clip-rule="evenodd"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M1 4a3 3 0 013-3h7a3 3 0 013 3v7a3 3 0 01-3 3H4a3 3 0 01-3-3V4zm3-2a2 2 0 00-2 2v7a2 2 0 002 2h7a2 2 0 002-2V4a2 2 0 00-2-2H4z" clip-rule="evenodd"/>
|
||||
<path fill="@image.color2" fill-rule="evenodd" d="M4 7.5a.5.5 0 01.5-.5h6a.5.5 0 010 1h-6a.5.5 0 01-.5-.5z" clip-rule="evenodd"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@format='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0_3639_261)">
|
||||
<path fill="@color3" d="M5.55 8.5H2A1.5 1.5 0 00.5 10v2A1.5 1.5 0 002 13.5h12a1.5 1.5 0 001.5-1.5v-2A1.5 1.5 0 0014 8.5h-3.55c-.63.61-1.49 1-2.45 1a3.48 3.48 0 01-2.45-1z"/>
|
||||
<path fill="@image.color1" d="M2 9a1 1 0 00-1 1v2a1 1 0 001 1h12a1 1 0 001-1v-2a1 1 0 00-1-1h-3.5V8H14a2 2 0 012 2v2a2 2 0 01-2 2H2a2 2 0 01-2-2v-2a2 2 0 012-2h3.5v1H2z"/>
|
||||
<path fill="@image.color1" d="M13 10.75a.75.75 0 11-1.5 0 .75.75 0 011.5 0z"/>
|
||||
<path fill="@image.color2" d="M5.85.14a.5.5 0 010 .70L4.70 2H8a4 4 0 11-4 4 .5.5 0 011 0 3 3 0 103-3H4.70l1.14 1.14a.5.5 0 11-.70.70l-2-2a.5.5 0 010-.70l2-2a.5.5 0 01.70 0z"/>
|
||||
</g>
|
||||
<defs>
|
||||
<clipPath id="clip0_3639_261">
|
||||
<path fill="#fff" d="M0 0h16v16H0z"/>
|
||||
</clipPath>
|
||||
</defs>
|
||||
</svg>'
|
||||
|
||||
@eject='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M7.37.82L1.76 9.33a.75.75 0 00.62 1.16h11.21a.75.75 0 00.62-1.16L8.62.82a.75.75 0 00-1.25 0z"/>
|
||||
<path fill="@image.color2" d="M8.20 1.1a.25.25 0 00-.41 0L2.18 9.61a.25.25 0 00.21.38h11.21a.25.25 0 00.20-.38L8.21 1.10zM6.95.55a1.25 1.25 0 012.08 0l5.60 8.51A1.25 1.25 0 0113.60 11H2.39a1.25 1.25 0 01-1.04-1.93L6.95.55zM1 13.5a.5.5 0 01.5-.5h13a.5.5 0 010 1h-13a.5.5 0 01-.5-.5z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@content='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M1.5 2.5a1 1 0 011-1h2a1 1 0 011 1v1a1 1 0 01-1 1h-2a1 1 0 01-1-1v-1z"/>
|
||||
<path fill="@image.color1" d="M1 2.5A1.5 1.5 0 012.5 1h2A1.5 1.5 0 016 2.5v1A1.5 1.5 0 014.5 5h-2A1.5 1.5 0 011 3.5v-1zM2.5 2a.5.5 0 00-.5.5v1a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-1a.5.5 0 00-.5-.5h-2z"/>
|
||||
<path fill="@color3" d="M1.5 7.5a1 1 0 011-1h2a1 1 0 011 1v1a1 1 0 01-1 1h-2a1 1 0 01-1-1v-1z"/>
|
||||
<path fill="@image.color1" d="M1 7.5A1.5 1.5 0 012.5 6h2A1.5 1.5 0 016 7.5v1A1.5 1.5 0 014.5 10h-2A1.5 1.5 0 011 8.5v-1zM2.5 7a.5.5 0 00-.5.5v1a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-1a.5.5 0 00-.5-.5h-2z"/>
|
||||
<path fill="@color3" d="M1.5 12.5a1 1 0 011-1h2a1 1 0 011 1v1a1 1 0 01-1 1h-2a1 1 0 01-1-1v-1z"/>
|
||||
<path fill="@image.color1" d="M1 12.5A1.5 1.5 0 012.5 11h2A1.5 1.5 0 016 12.5v1A1.5 1.5 0 014.5 15h-2A1.5 1.5 0 011 13.5v-1zm1.5-.5a.5.5 0 00-.5.5v1a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-1a.5.5 0 00-.5-.5h-2zM8 12.5a.5.5 0 01.5-.5h6a.5.5 0 010 1h-6a.5.5 0 01-.5-.5zM8 7.5a.5.5 0 01.5-.5h6a.5.5 0 010 1h-6a.5.5 0 01-.5-.5zM8 2.5a.5.5 0 01.5-.5h6a.5.5 0 010 1h-6a.5.5 0 01-.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@details='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M.5 6a.5.5 0 000 1h15a.5.5 0 000-1H.5zM.5 12a.5.5 0 000 1h15a.5.5 0 000-1H.5zM.5 9a.5.5 0 000 1h15a.5.5 0 000-1H.5zM.5 3a.5.5 0 000 1h15a.5.5 0 000-1H.5z"/>
|
||||
</svg>'
|
||||
|
||||
@extra_large_icons='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M1.5 3A1.5 1.5 0 013 1.5h10A1.5 1.5 0 0114.5 3v8a1.5 1.5 0 01-1.5 1.5H3A1.5 1.5 0 011.5 11V3z"/>
|
||||
<path fill="@image.color1" d="M1 3a2 2 0 012-2h10a2 2 0 012 2v8a2 2 0 01-2 2H3a2 2 0 01-2-2V3zm2-1a1 1 0 00-1 1v8a1 1 0 001 1h10a1 1 0 001-1V3a1 1 0 00-1-1H3zM3.5 14a.5.5 0 000 1h9a.5.5 0 000-1h-9z"/>
|
||||
</svg>'
|
||||
|
||||
@large_icons='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M2.5 4A1.5 1.5 0 014 2.5h8A1.5 1.5 0 0113.5 4v6a1.5 1.5 0 01-1.5 1.5H4A1.5 1.5 0 012.5 10V4z"/>
|
||||
<path fill="@image.color1" d="M2 4a2 2 0 012-2h8a2 2 0 012 2v6a2 2 0 01-2 2H4a2 2 0 01-2-2V4zm2-1a1 1 0 00-1 1v6a1 1 0 001 1h8a1 1 0 001-1V4a1 1 0 00-1-1H4zM2.5 13a.5.5 0 000 1h11a.5.5 0 000-1h-11z"/>
|
||||
</svg>'
|
||||
|
||||
@list='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M.5 6a.5.5 0 000 1h6a.5.5 0 000-1h-6zM9.5 6a.5.5 0 000 1h6a.5.5 0 000-1h-6zM.5 12a.5.5 0 000 1h6a.5.5 0 000-1h-6zM9.5 12a.5.5 0 000 1h6a.5.5 0 000-1h-6zM.5 9a.5.5 0 000 1h6a.5.5 0 000-1h-6zM9.5 9a.5.5 0 000 1h6a.5.5 0 000-1h-6zM.5 3a.5.5 0 000 1h6a.5.5 0 000-1h-6zM9.5 3a.5.5 0 000 1h6a.5.5 0 000-1h-6z"/>
|
||||
</svg>'
|
||||
|
||||
@medium_icons='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M3.5 4A1.5 1.5 0 015 2.5h6A1.5 1.5 0 0112.5 4v4A1.5 1.5 0 0111 9.5H5A1.5 1.5 0 013.5 8V4z"/>
|
||||
<path fill="@image.color1" d="M3 4a2 2 0 012-2h6a2 2 0 012 2v4a2 2 0 01-2 2H5a2 2 0 01-2-2V4zm2-1a1 1 0 00-1 1v4a1 1 0 001 1h6a1 1 0 001-1V4a1 1 0 00-1-1H5zM4.5 11a.5.5 0 000 1h7a.5.5 0 000-1h-7zM4.5 13a.5.5 0 000 1h7a.5.5 0 000-1h-7z"/>
|
||||
</svg>'
|
||||
|
||||
@small_icons='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M1.5 3A1.5 1.5 0 013 1.5h2A1.5 1.5 0 016.5 3v2A1.5 1.5 0 015 6.5H3A1.5 1.5 0 011.5 5V3z"/>
|
||||
<path fill="@image.color1" d="M1 3a2 2 0 012-2h2a2 2 0 012 2v2a2 2 0 01-2 2H3a2 2 0 01-2-2V3zm2-1a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1V3a1 1 0 00-1-1H3z"/>
|
||||
<path fill="@color3" d="M9.5 3A1.5 1.5 0 0111 1.5h2A1.5 1.5 0 0114.5 3v2A1.5 1.5 0 0113 6.5h-2A1.5 1.5 0 019.5 5V3z"/>
|
||||
<path fill="@image.color1" d="M9 3a2 2 0 012-2h2a2 2 0 012 2v2a2 2 0 01-2 2h-2a2 2 0 01-2-2V3zm2-1a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1V3a1 1 0 00-1-1h-2z"/>
|
||||
<path fill="@color3" d="M1.5 11A1.5 1.5 0 013 9.5h2A1.5 1.5 0 016.5 11v2A1.5 1.5 0 015 14.5H3A1.5 1.5 0 011.5 13v-2z"/>
|
||||
<path fill="@image.color1" d="M1 11a2 2 0 012-2h2a2 2 0 012 2v2a2 2 0 01-2 2H3a2 2 0 01-2-2v-2zm2-1a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1H3z"/>
|
||||
<path fill="@color3" d="M9.5 11A1.5 1.5 0 0111 9.5h2a1.5 1.5 0 011.5 1.5v2a1.5 1.5 0 01-1.5 1.5h-2A1.5 1.5 0 019.5 13v-2z"/>
|
||||
<path fill="@image.color1" d="M9 11a2 2 0 012-2h2a2 2 0 012 2v2a2 2 0 01-2 2h-2a2 2 0 01-2-2v-2zm2-1a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1h-2z"/>
|
||||
</svg>'
|
||||
|
||||
@tiles='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M.5 4A1.5 1.5 0 012 2.5h2A1.5 1.5 0 015.5 4v1A1.5 1.5 0 014 6.5H2A1.5 1.5 0 01.5 5V4z"/>
|
||||
<path fill="@image.color1" d="M0 4a2 2 0 012-2h2a2 2 0 012 2v1a2 2 0 01-2 2H2a2 2 0 01-2-2V4zm2-1a1 1 0 00-1 1v1a1 1 0 001 1h2a1 1 0 001-1V4a1 1 0 00-1-1H2z"/>
|
||||
<path fill="@color3" d="M.5 11A1.5 1.5 0 012 9.5h2A1.5 1.5 0 015.5 11v1A1.5 1.5 0 014 13.5H2A1.5 1.5 0 01.5 12v-1z"/>
|
||||
<path fill="@image.color1" d="M0 11a2 2 0 012-2h2a2 2 0 012 2v1a2 2 0 01-2 2H2a2 2 0 01-2-2v-1zm2-1a1 1 0 00-1 1v1a1 1 0 001 1h2a1 1 0 001-1v-1a1 1 0 00-1-1H2zM8 3.5a.5.5 0 01.5-.5h7a.5.5 0 010 1h-7a.5.5 0 01-.5-.5zM8 10.5a.5.5 0 01.5-.5h7a.5.5 0 010 1h-7a.5.5 0 01-.5-.5z"/>
|
||||
</svg>'
|
||||
@install='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color2" d="M7.5 0a.5.5 0 01.5.5v10.79l3.14-3.14a.5.5 0 01.70.70l-4 4a.5.5 0 01-.70 0l-4-4a.5.5 0 11.70-.70L7 11.29V.5a.5.5 0 01.5-.5zm-6 12a.5.5 0 01.5.5v1A1.5 1.5 0 003.5 15h8a1.5 1.5 0 001.5-1.5v-1a.5.5 0 011 0v1a2.5 2.5 0 01-2.5 2.5h-8A2.5 2.5 0 011 13.5v-1a.5.5 0 01.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@select_all, 'Выбрать все'='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M0 2a2 2 0 012-2h.5a.5.5 0 010 1H2a1 1 0 00-1 1v.5a.5.5 0 01-1 0V2zM4.5.5A.5.5 0 015 0h2a.5.5 0 010 1H5a.5.5 0 01-.5-.5zM9 .5a.5.5 0 01.5-.5h2a.5.5 0 010 1h-2A.5.5 0 019 .5zm4 0a.5.5 0 01.5-.5h.5a2 2 0 012 2v.5a.5.5 0 01-1 0V2a1 1 0 00-1-1h-.5a.5.5 0 01-.5-.5zM.5 4a.5.5 0 01.5.5v2a.5.5 0 01-1 0v-2A.5.5 0 01.5 4zm15 0a.5.5 0 01.5.5v2a.5.5 0 01-1 0v-2a.5.5 0 01.5-.5zM.5 8.5A.5.5 0 011 9v2a.5.5 0 01-1 0V9a.5.5 0 01.5-.5zm15 0a.5.5 0 01.5.5v2a.5.5 0 01-1 0V9a.5.5 0 01.5-.5zM.5 13a.5.5 0 01.5.5v.5a1 1 0 001 1h.5a.5.5 0 010 1H2a2 2 0 01-2-2v-.5a.5.5 0 01.5-.5zm15 0a.5.5 0 01.5.5v.5a2 2 0 01-2 2h-.5a.5.5 0 010-1h.5a1 1 0 001-1v-.5a.5.5 0 01.5-.5zm-11 2.5A.5.5 0 015 15h2a.5.5 0 010 1H5a.5.5 0 01-.5-.5zm4.5 0a.5.5 0 01.5-.5h2a.5.5 0 010 1h-2a.5.5 0 01-.5-.5z"/>
|
||||
<path fill="@image.color2" d="M5.5 2.5h-2a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1zM5.5 9.5h-2a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1zM12.5 2.5h-2a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1zM12.5 9.5h-2a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1z"/>
|
||||
<path fill="@image.color2" d="M2 3.5A1.5 1.5 0 013.5 2h2A1.5 1.5 0 017 3.5v2A1.5 1.5 0 015.5 7h-2A1.5 1.5 0 012 5.5v-2zM3.5 3a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-2a.5.5 0 00-.5-.5h-2zm5.5.5A1.5 1.5 0 0110.5 2h2A1.5 1.5 0 0114 3.5v2A1.5 1.5 0 0112.5 7h-2A1.5 1.5 0 019 5.5v-2zm1.5-.5a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-2a.5.5 0 00-.5-.5h-2zM2 10.5A1.5 1.5 0 013.5 9h2A1.5 1.5 0 017 10.5v2A1.5 1.5 0 015.5 14h-2A1.5 1.5 0 012 12.5v-2zm1.5-.5a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-2a.5.5 0 00-.5-.5h-2zm5.5.5A1.5 1.5 0 0110.5 9h2a1.5 1.5 0 011.5 1.5v2a1.5 1.5 0 01-1.5 1.5h-2A1.5 1.5 0 019 12.5v-2zm1.5-.5a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-2a.5.5 0 00-.5-.5h-2z"/>
|
||||
</svg>'
|
||||
|
||||
@invert_selection='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color2" d="M5.5 9.5h-2a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1zM12.5 2.5h-2a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1z"/>
|
||||
<path fill="@image.color2" d="M9 3.5A1.5 1.5 0 0110.5 2h2A1.5 1.5 0 0114 3.5v2A1.5 1.5 0 0112.5 7h-2A1.5 1.5 0 019 5.5v-2zm1.5-.5a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-2a.5.5 0 00-.5-.5h-2zM2 10.5A1.5 1.5 0 013.5 9h2A1.5 1.5 0 017 10.5v2A1.5 1.5 0 015.5 14h-2A1.5 1.5 0 012 12.5v-2zm1.5-.5a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-2a.5.5 0 00-.5-.5h-2z"/>
|
||||
<path fill="@color3" d="M4.5 1.5h-2a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1zM13.5 10.5h-2a1 1 0 00-1 1v2a1 1 0 001 1h2a1 1 0 001-1v-2a1 1 0 00-1-1z"/>
|
||||
<path fill="@image.color1" d="M1 2.5A1.5 1.5 0 012.5 1h2A1.5 1.5 0 016 2.5v2A1.5 1.5 0 014.5 6h-2A1.5 1.5 0 011 4.5v-2zM2.5 2a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-2a.5.5 0 00-.5-.5h-2zm7.5 9.5a1.5 1.5 0 011.5-1.5h2a1.5 1.5 0 011.5 1.5v2a1.5 1.5 0 01-1.5 1.5h-2a1.5 1.5 0 01-1.5-1.5v-2zm1.5-.5a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-2a.5.5 0 00-.5-.5h-2zM0 8.25C0 7.56.56 7 1.25 7h.25a.5.5 0 010 1h-.25a.25.25 0 00-.25.25v.25a.5.5 0 01-1 0v-.25zm3-.75a.5.5 0 01.5-.5h2a.5.5 0 010 1h-2a.5.5 0 01-.5-.5zm4 0a.5.5 0 01.5-.5h.25C8.44 7 9 7.56 9 8.25v.25a.5.5 0 01-1 0v-.25A.25.25 0 007.75 8H7.5a.5.5 0 01-.5-.5zM.5 10a.5.5 0 01.5.5v2a.5.5 0 01-1 0v-2a.5.5 0 01.5-.5zm8 0a.5.5 0 01.5.5v2a.5.5 0 01-1 0v-2a.5.5 0 01.5-.5zm-8 4a.5.5 0 01.5.5v.25c0 .13.11.25.25.25h.25a.5.5 0 010 1h-.25C.56 16 0 15.44 0 14.75v-.25a.5.5 0 01.5-.5zm8 0a.5.5 0 01.5.5v.25C9 15.44 8.44 16 7.75 16H7.5a.5.5 0 010-1h.25a.25.25 0 00.25-.25v-.25a.5.5 0 01.5-.5zM3 15.5a.5.5 0 01.5-.5h2a.5.5 0 010 1h-2a.5.5 0 01-.5-.5zM7 1.25C7 .56 7.56 0 8.25 0h.25a.5.5 0 010 1h-.25a.25.25 0 00-.25.25v.25a.5.5 0 01-1 0v-.25zm3-.75a.5.5 0 01.5-.5h2a.5.5 0 010 1h-2a.5.5 0 01-.5-.5zm4 0a.5.5 0 01.5-.5h.25C15.44 0 16 .56 16 1.25v.25a.5.5 0 01-1 0v-.25a.25.25 0 00-.25-.25h-.25a.5.5 0 01-.5-.5zM7.5 3a.5.5 0 01.5.5v2a.5.5 0 01-1 0v-2a.5.5 0 01.5-.5zm8 0a.5.5 0 01.5.5v2a.5.5 0 01-1 0v-2a.5.5 0 01.5-.5zm0 4a.5.5 0 01.5.5v.25C16 8.44 15.44 9 14.75 9h-.25a.5.5 0 010-1h.25a.25.25 0 00.25-.25V7.5a.5.5 0 01.5-.5zM10 8.5a.5.5 0 01.5-.5h2a.5.5 0 010 1h-2a.5.5 0 01-.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@select_none='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M5.5 1.5h-3a1 1 0 00-1 1v3a1 1 0 001 1h3a1 1 0 001-1v-3a1 1 0 00-1-1zM13.5 1.5h-3a1 1 0 00-1 1v3a1 1 0 001 1h3a1 1 0 001-1v-3a1 1 0 00-1-1zM13.5 9.5h-3a1 1 0 00-1 1v3a1 1 0 001 1h3a1 1 0 001-1v-3a1 1 0 00-1-1zM6.5 13.5v-3a1 1 0 00-1-1h-3a1 1 0 00-1 1v3a1 1 0 001 1h3a1 1 0 001-1z"/>
|
||||
<path fill="@image.color1" d="M1 2.5A1.5 1.5 0 012.5 1h3A1.5 1.5 0 017 2.5v3A1.5 1.5 0 015.5 7h-3A1.5 1.5 0 011 5.5v-3zM2.5 2a.5.5 0 00-.5.5v3a.5.5 0 00.5.5h3a.5.5 0 00.5-.5v-3a.5.5 0 00-.5-.5h-3zm6.5.5A1.5 1.5 0 0110.5 1h3A1.5 1.5 0 0115 2.5v3A1.5 1.5 0 0113.5 7h-3A1.5 1.5 0 019 5.5v-3zm1.5-.5a.5.5 0 00-.5.5v3a.5.5 0 00.5.5h3a.5.5 0 00.5-.5v-3a.5.5 0 00-.5-.5h-3zm-8 8a.5.5 0 00-.5.5v3a.5.5 0 00.5.5h3a.5.5 0 00.5-.5v-3a.5.5 0 00-.5-.5h-3zm-1.5.5A1.5 1.5 0 012.5 9h3A1.5 1.5 0 017 10.5v3A1.5 1.5 0 015.5 15h-3A1.5 1.5 0 011 13.5v-3zm8 0A1.5 1.5 0 0110.5 9h3a1.5 1.5 0 011.5 1.5v3a1.5 1.5 0 01-1.5 1.5h-3A1.5 1.5 0 019 13.5v-3zm1.5-.5a.5.5 0 00-.5.5v3a.5.5 0 00.5.5h3a.5.5 0 00.5-.5v-3a.5.5 0 00-.5-.5h-3z"/>
|
||||
</svg>'
|
||||
|
||||
@share, share_with='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M1 4.5A2.5 2.5 0 013.5 2h3a.5.5 0 010 1h-3A1.5 1.5 0 002 4.5v8A1.5 1.5 0 003.5 14h8a1.5 1.5 0 001.5-1.5v-1a.5.5 0 011 0v1a2.5 2.5 0 01-2.5 2.5h-8A2.5 2.5 0 011 12.5v-8z"/>
|
||||
<path fill="@color3" d="M15.11 6L10.5 1.5v2.67c-5.10 0-6.35 4.32-6.35 6.32 2.53-2.23 4.5-2.53 6.38-2.72L10.5 10.5 15.11 6z"/>
|
||||
<path fill="@image.color2" d="M10.95 10.83l4.49-4.42.05-.06a.58.58 0 00-.05-.76l-4.49-4.42-.06-.05a.56.56 0 00-.89.46v2.13l-.22.01c-3.56.28-5.64 2.53-6.14 6.62a.57.57 0 00.95.48A9.61 9.61 0 019 8.46a7.67 7.67 0 01.74-.11L10 8.32v2.09l.00.08a.56.56 0 00.94.33zM9.85 4.72L11 4.64V2.61l3.44 3.38L11 9.39V7.23l-1.35.12h-.00a9.72 9.72 0 00-4.82 2.00 6.48 6.48 0 011.47-3.06A5.2 5.2 0 019.84 4.72z"/>
|
||||
</svg>'
|
||||
|
||||
@mount='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M9.89 6.5A5.75 5.75 0 01.5 8.63V10A1.5 1.5 0 002 11.5h12a1.5 1.5 0 001.5-1.5V8A1.5 1.5 0 0014 6.5H9.89z"/>
|
||||
<path fill="@image.color1" d="M9.68 7H14a1 1 0 011 1v2a1 1 0 01-1 1H2a1 1 0 01-1-1v-.93a5.78 5.78 0 01-1-.98V10a2 2 0 002 2h12a2 2 0 002-2V8a2 2 0 00-2-2h-3.94c-.09.34-.21.68-.37 1z"/>
|
||||
<path fill="@image.color1" d="M13 8.75a.75.75 0 11-1.5 0 .75.75 0 011.5 0z"/>
|
||||
<path fill="@image.color2" d="M0 4.5a4.5 4.5 0 119 0 4.5 4.5 0 01-9 0z"/>
|
||||
<path fill="#fff" d="M6.89 4.89a.56.56 0 01-.79 0L4.5 3.29 2.89 4.89a.56.56 0 01-.79-.79l2-2c.22-.22.57-.22.79 0l2 2c.22.22.22.57 0 .79z"/>
|
||||
<path fill="#fff" d="M4.5 7a.5.5 0 01-.5-.5v-4a.5.5 0 011 0v4a.5.5 0 01-.5.5z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@new, new_item='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M14.5 7.5a7 7 0 11-14 0 7 7 0 0114 0z"/>
|
||||
<path fill="@image.color1" d="M7.5 1a6.5 6.5 0 100 13 6.5 6.5 0 000-13zM0 7.5a7.5 7.5 0 1115 0 7.5 7.5 0 01-15 0z"/>
|
||||
<path fill="@image.color2" d="M7.5 4a.5.5 0 01.5.5V7h2.5a.5.5 0 010 1H8v2.5a.5.5 0 01-1 0V8H4.5a.5.5 0 010-1H7V4.5a.5.5 0 01.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@new_folder='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M2.5 1.5h3a2 2 0 011.6.8L8 3.5h5.5a2 2 0 012 2v1.87a5.75 5.75 0 00-8.90 7.13H2.5a2 2 0 01-2-2v-9a2 2 0 012-2z"/>
|
||||
<path fill="@image.color1" d="M0 3.5A2.5 2.5 0 012.5 1h3a2.5 2.5 0 012 1l.75 1h5.25A2.5 2.5 0 0116 5.5v2.42a5.78 5.78 0 00-1-.98V5.5A1.5 1.5 0 0013.5 4H8.15l-.87.58A2.5 2.5 0 015.89 5H1v7.5A1.5 1.5 0 002.5 14h3.82c.17.35.38.69.61 1H2.5A2.5 2.5 0 010 12.5v-9zM2.5 2A1.5 1.5 0 001 3.5V4h4.89a1.5 1.5 0 00.83-.25l.55-.37L6.7 2.6A1.5 1.5 0 005.5 2h-3z"/>
|
||||
<path fill="@image.color2" d="M16 11.5a4.5 4.5 0 11-9 0 4.5 4.5 0 019 0z"/>
|
||||
<path fill="@if(theme.islight,'#fff','#000')" d="M11.5 9a.5.5 0 01.5.5V11h1.5a.5.5 0 010 1H12v1.5a.5.5 0 01-1 0V12H9.5a.5.5 0 010-1H11V9.5a.5.5 0 01.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@new_file='<svg viewBox="-10 0 2058 2048">
|
||||
<path fill="@image.color1" d="M1920 784v1013q0 50 -20.5 95.5t-55 80t-80 55t-95.5 20.5h-507q35 -28 67 -60t59 -68h376q27 0 50 -10t40.5 -27.5t27.5 -40.5t10 -50v-1008v-8t-1 -8h-388q-52 0 -97.5 -21t-79.5 -56t-54 -81.5t-20 -97.5v-383q-4 -1 -8 -1h-8h-496q-27 0 -50 10t-40.5 27.5t-27.5 40.5t-10 50v505q-67 18 -128 48v-558q0 -50 20.5 -95.5t55 -80t80 -55t95.5 -20.5h501q51 0 98 19.5t83 55.5l528 528q36 36 55.5 83t19.5 98zM1280 512q0 27 10 50.5t27 40.5t40.5 27t50.5 10h294l-422 -422v294z" />
|
||||
<path fill="@image.color2" d="M126 1462q0 -119 45.5 -224t123.5 -183t183 -123.5t224 -45.5q79 0 152.5 20.5t137.5 58t117 90.5t90.5 117t58 137.5t20.5 152.5q0 119 -45.5 224t-123.5 183t-183 123.5t-224 45.5q-120 0 -225 -45t-183 -123t-123 -183t-45 -225zM766 1526h192q26 0 45 -19t19 -45t-19 -45t-45 -19h-192v-192q0 -26 -19 -45t-45 -19t-45 19t-19 45v192h-192q-26 0 -45 19t-19 45t19 45t45 19h192v192q0 26 19 45t45 19t45 -19t19 -45v-192z"/>
|
||||
</svg>'
|
||||
|
||||
@open_folder,open_folder_location, open_file_location, open_as_portable='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M5.75 1.5H2A1.5 1.5 0 00.5 3v10A1.5 1.5 0 002 14.5h10.94a1.5 1.5 0 001.48-1.29l1.01-7.27a.37.37 0 00-.37-.43.56.56 0 01-.56-.56V4.5a1 1 0 00-1-1H8L6.95 2.1a1.5 1.5 0 00-1.2-.6z"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M0 3a2 2 0 012-2h3.75a2 2 0 011.6.8l.9 1.2H13a2 2 0 012 2v.14a1.5 1.5 0 01.83 1.56l-.91 6.56A2 2 0 0112.94 15H2a2 2 0 01-2-2V3zm14 2a1 1 0 00-1-1H7.75l-1.2-1.6a1 1 0 00-.8-.4H2a1 1 0 00-1 1v9.73l1.26-6.13A2 2 0 014.22 5H14zM1.76 13.97c.07.01.15.02.23.02h10.94a1 1 0 00.99-.86l.91-6.57A.5.5 0 0014.35 6H4.22a1 1 0 00-.97.79l-1.47 7.17z"/>
|
||||
</svg>'
|
||||
|
||||
@open_new_window, open_in_new_window, open_in_new_process='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color2" d="M8 1.5a.5.5 0 01.5-.5h6a.5.5 0 01.5.5v6a.5.5 0 01-1 0V2.70L7.85 8.85a.5.5 0 11-.70-.70L13.29 2H8.5a.5.5 0 01-.5-.5z"/>
|
||||
<path fill="@image.color1" d="M1 4.5A2.5 2.5 0 013.5 2h3a.5.5 0 010 1h-3A1.5 1.5 0 002 4.5v8A1.5 1.5 0 003.5 14h8a1.5 1.5 0 001.5-1.5v-3a.5.5 0 011 0v3a2.5 2.5 0 01-2.5 2.5h-8A2.5 2.5 0 011 12.5v-8z"/>
|
||||
</svg>'
|
||||
|
||||
@open_new_tab, open_in_new_tab='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M13 1.5H5A1.5 1.5 0 003.5 3v8A1.5 1.5 0 005 12.5h8a1.5 1.5 0 001.5-1.5V3A1.5 1.5 0 0013 1.5z"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M5 1a2 2 0 00-2 2 2 2 0 00-2 2v7a3 3 0 003 3h7a2 2 0 002-2 2 2 0 002-2V3a2 2 0 00-2-2H5zm7 12H5a2 2 0 01-2-2V4a1 1 0 00-1 1v7a2 2 0 002 2h7a1 1 0 001-1zM4 3a1 1 0 011-1h8a1 1 0 011 1v8a1 1 0 01-1 1H5a1 1 0 01-1-1V3z" clip-rule="evenodd"/>
|
||||
<path fill="@image.color2" fill-rule="evenodd" d="M7 4.5a.5.5 0 01.5-.5h4a.5.5 0 01.5.5v4a.5.5 0 01-1 0V5.70L6.85 9.85a.5.5 0 01-.70-.70L10.29 5H7.5a.5.5 0 01-.5-.5z" clip-rule="evenodd"/>
|
||||
</svg>'
|
||||
|
||||
@open_spot_light='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path d="M13.03 1C13.29 1 13.54 1.05 13.78 1.16C14.02 1.26 14.22 1.41 14.40 1.59C14.58 1.77 14.73 1.97 14.83 2.21C14.94 2.45 15 2.70 15 2.96V11.03C15 11.29 14.94 11.54 14.84 11.78C14.73 12.01 14.59 12.22 14.41 12.40C14.23 12.58 14.03 12.72 13.79 12.83C13.56 12.94 13.31 13 13.06 13H13V13.03C13 13.29 12.94 13.54 12.83 13.78C12.73 14.02 12.58 14.23 12.40 14.41C12.22 14.59 12.02 14.73 11.78 14.84C11.54 14.94 11.29 15 11.03 15H3.93C3.54 15 3.17 14.92 2.81 14.76C2.45 14.60 2.14 14.39 1.87 14.12C1.60 13.85 1.39 13.54 1.23 13.18C1.07 12.82 1 12.45 1 12.06V5C1 4.74 1.04 4.49 1.14 4.25C1.25 4.01 1.39 3.79 1.57 3.61C1.74 3.42 1.95 3.28 2.18 3.17C2.42 3.05 2.67 3 2.93 3H3V2.96C3 2.70 3.05 2.45 3.15 2.21C3.26 1.97 3.40 1.77 3.58 1.59C3.76 1.41 3.97 1.26 4.21 1.16C4.45 1.05 4.70 1 4.96 1H13.03ZM14 3C14 2.86 13.97 2.73 13.92 2.61C13.86 2.49 13.79 2.38 13.70 2.29C13.61 2.20 13.50 2.13 13.38 2.07C13.26 2.02 13.13 2 13 2H5C4.85 2 4.72 2.02 4.60 2.07C4.48 2.13 4.38 2.20 4.28 2.29C4.20 2.38 4.13 2.48 4.07 2.60C4.02 2.72 4 2.85 4 3V11C4 11.14 4.02 11.27 4.07 11.39C4.13 11.51 4.20 11.62 4.28 11.71C4.37 11.79 4.48 11.86 4.60 11.92C4.72 11.97 4.85 12 5 12H13C13.14 12 13.27 11.97 13.39 11.92C13.51 11.86 13.61 11.79 13.70 11.71C13.79 11.61 13.86 11.51 13.92 11.39C13.97 11.27 14 11.14 14 11V3ZM12 13H4.96C4.69 13 4.43 12.94 4.19 12.83C3.96 12.72 3.75 12.58 3.57 12.39C3.40 12.21 3.26 12.00 3.15 11.76C3.05 11.52 3 11.26 3 11V4C2.85 4 2.72 4.02 2.60 4.07C2.48 4.13 2.38 4.20 2.28 4.29C2.20 4.38 2.13 4.48 2.07 4.60C2.02 4.72 2 4.85 2 5V12.03C2 12.29 2.05 12.54 2.15 12.78C2.26 13.02 2.40 13.23 2.58 13.41C2.76 13.59 2.97 13.73 3.21 13.84C3.45 13.94 3.70 14 3.96 14H11C11.14 14 11.27 13.97 11.39 13.92C11.51 13.86 11.61 13.79 11.70 13.71C11.79 13.61 11.86 13.51 11.92 13.39C11.97 13.27 12 13.14 12 13Z" fill="black"/>
|
||||
<path d="M11.85 4.14C11.75 4.04 11.63 4 11.5 4H7.5C7.36 4 7.24 4.04 7.14 4.14C7.04 4.24 7 4.36 7 4.5C7 4.63 7.04 4.75 7.14 4.85C7.24 4.95 7.36 5 7.5 5H10.29L6.14 9.14C6.04 9.24 6 9.36 6 9.5C6 9.63 6.04 9.75 6.14 9.85C6.24 9.95 6.36 10 6.5 10C6.63 10 6.75 9.95 6.85 9.85L11 5.70V8.5C11 8.63 11.04 8.75 11.14 8.85C11.24 8.95 11.36 9 11.5 9C11.63 9 11.75 8.95 11.85 8.85C11.95 8.75 12 8.63 12 8.5V4.5C12 4.36 11.95 4.24 11.85 4.14Z" fill="#0C59A4"/>
|
||||
</svg>'
|
||||
|
||||
@open_with='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M4 1.5H2a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5V2a.5.5 0 00-.5-.5zM4 6.5H2a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5V7a.5.5 0 00-.5-.5zM4 11.5H2a.5.5 0 00-.5.5v2a.5.5 0 00.5.5h2a.5.5 0 00.5-.5v-2a.5.5 0 00-.5-.5z"/>
|
||||
<path fill="@image.color1" d="M1 2a1 1 0 011-1h2a1 1 0 011 1v2a1 1 0 01-1 1H2a1 1 0 01-1-1V2zm3 0H2v2h2V2zM1 7a1 1 0 011-1h2a1 1 0 011 1v2a1 1 0 01-1 1H2a1 1 0 01-1-1V7zm3 0H2v2h2V7zm-3 5a1 1 0 011-1h2a1 1 0 011 1v2a1 1 0 01-1 1H2a1 1 0 01-1-1v-2zm3 0H2v2h2v-2zM6.5 2a.5.5 0 000 1h8a.5.5 0 000-1h-8zM6.5 7a.5.5 0 000 1h.43c.28-.37.61-.70.98-1H6.5z"/>
|
||||
<path fill="@image.color2" d="M7 11.5a4.5 4.5 0 119 0 4.5 4.5 0 01-9 0z"/>
|
||||
<path fill="@if(theme.islight,'#fff','#000')" d="M13 12.5a.5.5 0 101 0v-3a.5.5 0 00-.5-.5h-3a.5.5 0 100 1h1.73l-2.61 2.61a.54.54 0 10.76.76L13 10.76V12.5z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@run_with_powershell, open_windows_powershell, open_powershell_window_here,windows_powershell,windows_powershell_admin='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M2.17 3.62l-1.23 8a2.5 2.5 0 002.47 2.88H6.75V8.36c0-1.72 1.86-2.81 3.36-1.95l4.25 2.43.68-4.45a2.5 2.5 0 00-2.47-2.88H4.64a2.5 2.5 0 00-2.47 2.12z"/>
|
||||
<path fill="@image.color1" d="M1.43 11.69L2.46 5h11.98l-.55 3.57.93.53.71-4.64A3 3 0 0012.58 1H4.64A3 3 0 001.68 3.54l-1.23 8A3 3 0 003.41 15h3.36a2.32 2.32 0 01-.02-.36V14H3.41a2 2 0 01-1.97-2.30zM4.64 2h7.94a2 2 0 012.00 2H2.62l.04-.30A2 2 0 014.64 2z"/>
|
||||
<path fill="@image.color2" d="M9.49 7.49A1 1 0 008 8.36v6.27a1 1 0 001.49.86l5.49-3.13a1 1 0 000-1.73L9.49 7.49z"/>
|
||||
</svg>'
|
||||
|
||||
@properties='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M12 6l-2-2L13.00.99A4.45 4.45 0 0011 .5 4.5 4.5 0 006.5 5c.00.43.07.87.20 1.28l-5.58 5.58a2.12 2.12 0 103.00 3.00L9.71 9.29c.41.13.85.20 1.28.20A4.5 4.5 0 0015.5 5a4.44 4.44 0 00-.49-2.00L12 6z"/>
|
||||
<path fill="@image.color1" d="M7.46 1.46A5 5 0 0111 0h.00a4.95 4.95 0 012.23.54.5.5 0 01.12.79L10.70 4 12 5.29l2.65-2.65a.5.5 0 01.79.12A4.95 4.95 0 0116 4.99V5a5 5 0 01-5 5h-.00a4.95 4.95 0 01-1.13-.14l-5.37 5.37a2.62 2.62 0 01-4.28-.85 2.62 2.62 0 01.57-2.86l5.37-5.38A4.95 4.95 0 016 5.00V5a5 5 0 011.46-3.53zM10.99 1A4 4 0 007 4.99c.00.38.06.77.18 1.13a.5.5 0 01-.12.50l-5.58 5.58a1.62 1.62 0 00-.35 1.77 1.62 1.62 0 002.65.52l5.58-5.58a.5.5 0 01.50-.12c.36.11.75.18 1.13.18A4 4 0 0015 5.00a3.94 3.94 0 00-.17-1.12l-2.47 2.47a.5.5 0 01-.70 0l-2-2a.5.5 0 010-.70l2.47-2.47A3.95 3.95 0 0010.99 1z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@restore='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@image.color2" d="M3.85.14a.5.5 0 010 .70L1.70 3H8.5A6.5 6.5 0 112 9.5a.5.5 0 011 0A5.5 5.5 0 108.5 4H1.70l2.14 2.14a.5.5 0 11-.70.70l-3-3a.5.5 0 010-.70l3-3a.5.5 0 01.70 0z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@undo, undo_copy, undo_move, undo_delete, undo_rename, undo_new, undo_apply_properties='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@image.color2" d="M2.5 0a.5.5 0 01.5.5V5h4.5a.5.5 0 010 1h-5a.5.5 0 01-.5-.5v-5a.5.5 0 01.5-.5z"/>
|
||||
<path fill="@image.color2" d="M8.51.22A5 5 0 0113.2 8.84l-8.37 7.04a.5.5 0 11-.64-.76l8.37-7.04.00-.00A4 4 0 007.44 1.92L2.94 5.67a.5.5 0 01-.64-.76L6.8 1.15A5.00 5.00 0 018.51.22z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@redo, redo_copy, redo_move, redo_delete, redo_rename, redo_new, redo_apply_properties='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@image.color2" d="M13.5 0a.5.5 0 01.5.5v5a.5.5 0 01-.5.5h-5a.5.5 0 010-1H13V.5a.5.5 0 01.5-.5z"/>
|
||||
<path fill="@image.color2" d="M7.18 1.18a4.00 4.00 0 011.37.74l4.49 3.74a.5.5 0 00.64-.76L9.2 1.15A5 5 0 002.8 8.84h.00l8.37 7.04a.5.5 0 10.64-.76l-8.38-7.04-.00-.00A4 4 0 017.18 1.18z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@refresh='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M14.5 0a.5.5 0 01.5.5v4a.5.5 0 01-.5.5h-4a.5.5 0 010-1H14V.5a.5.5 0 01.5-.5z"/>
|
||||
<path fill="@image.color1" d="M8 1a7 7 0 107 7 .5.5 0 011 0 8 8 0 11-1.36-4.47.5.5 0 01-.82.56A6.99 6.99 0 008 1z"/>
|
||||
</svg>'
|
||||
|
||||
@rename='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M3 2.5h6v11H3A2.5 2.5 0 01.5 11V5A2.5 2.5 0 013 2.5zM13 2.5h-1v11h1a2.5 2.5 0 002.5-2.5V5A2.5 2.5 0 0013 2.5z"/>
|
||||
<path stroke="@image.color1" d="M9 2.5H3A2.5 2.5 0 00.5 5v6A2.5 2.5 0 003 13.5h6m3-11h1A2.5 2.5 0 0115.5 5v6a2.5 2.5 0 01-2.5 2.5h-1"/>
|
||||
<path stroke="@image.color2" stroke-linecap="round" d="M8.5.5h2m2 0h-2m-2 15h2m2 0h-2m0-15v15"/>
|
||||
<path fill="@image.color2" fill-rule="evenodd" d="M5.5 4a.5.5 0 01.45.29l2.75 6a.5.5 0 11-.91.41L7.12 9.25H3.87l-.66 1.45a.5.5 0 11-.91-.41l2.75-6A.50.50 0 015.5 4zm0 1.7L4.33 8.25H6.67L5.5 5.7z" clip-rule="evenodd"/>
|
||||
</svg>'
|
||||
|
||||
@rotate_left='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M1.5 14.5v-7l13 7h-13z"/>
|
||||
<path fill="@image.color1" d="M1.24 7.07A.5.5 0 001 7.5v7a.5.5 0 00.5.5h13a.5.5 0 00.23-.94l-13-7a.5.5 0 00-.49.01zM12.51 14H2V8.33L12.51 14z"/>
|
||||
<path fill="@image.color2" d="M6.85 1.14a.5.5 0 00-.70 0l-2 2a.5.5 0 000 .70l2 2a.5.5 0 10.70-.70L5.70 4H10.5c1.00 0 1.9.30 2.52.77.63.47.97 1.08.97 1.72 0 .63-.34 1.25-.97 1.72C12.4 8.69 11.50 9 10.5 9a.5.5 0 000 1c1.20 0 2.31-.36 3.12-.97C14.44 8.40 15 7.52 15 6.5s-.55-1.90-1.37-2.52C12.81 3.36 11.70 3 10.5 3H5.70l1.14-1.14a.5.5 0 000-.70z"/>
|
||||
</svg>'
|
||||
|
||||
@rotate_right='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M14.5 14.5v-7l-13 7h13z"/>
|
||||
<path fill="@image.color1" d="M14.75 7.07A.5.5 0 0115 7.5v7a.5.5 0 01-.5.5h-13a.5.5 0 01-.23-.94l13-7a.5.5 0 01.49.01zM3.48 14H14V8.33L3.48 14z"/>
|
||||
<path fill="@image.color2" d="M9.14 1.14a.5.5 0 01.70 0l2 2a.5.5 0 010 .70l-2 2a.5.5 0 11-.70-.70L10.29 4H5.5c-1.00 0-1.9.30-2.52.77C2.34 5.25 2 5.86 2 6.5c0 .63.34 1.25.97 1.72C3.6 8.69 4.49 9 5.5 9a.5.5 0 010 1c-1.20 0-2.31-.36-3.12-.97C1.55 8.40 1 7.52 1 6.5s.55-1.90 1.37-2.52C3.19 3.36 4.29 3 5.5 3h4.79L9.14 1.85a.5.5 0 010-.70z"/>
|
||||
</svg>'
|
||||
|
||||
@set_as_desktop_wallpaper, set_as_desktop_background='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M.5 9.37A3.48 3.48 0 002.50 10h4a3.5 3.5 0 003.5-3.5v-4H13A2.5 2.5 0 0115.5 5v6a2.5 2.5 0 01-2.5 2.5H3A2.5 2.5 0 01.5 11V9.37z"/>
|
||||
<path fill="@image.color1" d="M0 8.94V11a3 3 0 003 3h10a3 3 0 003-3V5a3 3 0 00-3-3H9.96c.02.16.03.33.03.5V3H13a2 2 0 012 2v5H1v-.33a3.51 3.51 0 01-1-.71zM3 13a2 2 0 01-2-2h10.5a.5.5 0 100 1 .5.5 0 000-1h2a.5.5 0 100 1 .5.5 0 000-1H15a2 2 0 01-2 2H3z"/>
|
||||
<path fill="@image.color2" d="M2.50 0a2.5 2.5 0 00-2.5 2.5v4c0 .51.15.98.41 1.37l3.02-3.02a1.5 1.5 0 012.12 0l3.02 3.02c.26-.39.41-.87.41-1.37v-4a2.5 2.5 0 00-2.5-2.5h-4zm3.75 3.5a.75.75 0 110-1.5.75.75 0 010 1.5z"/>
|
||||
<path fill="@image.color2" d="M2.50 9c-.51 0-.98-.15-1.37-.41L4.14 5.56a.5.5 0 01.70 0l3.02 3.02C7.48 8.84 7.01 9 6.50 9h-4z"/>
|
||||
</svg>'
|
||||
|
||||
@next_desktop_background='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M2.5 10v3A2.5 2.5 0 005 15.5h8a2.5 2.5 0 002.5-2.5V5A2.5 2.5 0 0013 2.5h-3V9a1 1 0 01-1 1H2.5z"/>
|
||||
<path fill="@image.color1" d="M2 10v3a3 3 0 003 3h8a3 3 0 003-3V5a3 3 0 00-3-3h-3v1h3a2 2 0 012 2v8c0 .37-.10.71-.27 1.01L10.23 9.53a1.75 1.75 0 00-.28-.23A1 1 0 019 10H7.29l-4.01 4.01A1.99 1.99 0 013 13v-3H2zm1.98 4.72l4.48-4.48a.75.75 0 011.06 0l4.48 4.48A1.99 1.99 0 0113 15H5c-.37 0-.71-.10-1.01-.27z"/>
|
||||
<path fill="@image.color1" d="M10 6.5a1.5 1.5 0 103 0 1.5 1.5 0 00-3 0zm1.5-.5a.5.5 0 110 1 .5.5 0 010-1z"/>
|
||||
<g>
|
||||
<path fill="@image.color2" d="M9 .5a.5.5 0 00-1 0v8a.5.5 0 001 0v-8zM5.98 4.10L.80.11A.5.5 0 000 .51v7.97a.5.5 0 00.80.39l5.18-3.98a.5.5 0 000-.79z"/>
|
||||
</g>
|
||||
</svg>'
|
||||
|
||||
@desktop, show_desktop, show_desktop_icons,show_the_desktop='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M.53 6h1.59a4.00 4.00 0 007.74 0H11.5v-.00a1.50 1.50 0 001.44-1.89 6.60 6.60 0 00-.67-1.59H13A2.5 2.5 0 0115.5 5v6a2.5 2.5 0 01-2.5 2.5H3A2.5 2.5 0 01.5 11V6h.03z"/>
|
||||
<path fill="@image.color1" d="M1 6H.53A1.5 1.5 0 010 5.91V11a3 3 0 003 3h10a3 3 0 003-3V5a3 3 0 00-3-3h-1.05c.22.31.42.64.59 1H13a2 2 0 012 2v5H1V6zm2 7a2 2 0 01-2-2h10.5a.5.5 0 100 1 .5.5 0 000-1h2a.5.5 0 100 1 .5.5 0 000-1H15a2 2 0 01-2 2H3z"/>
|
||||
<path fill="@image.color2" d="M.98 4.63C1.54 2.56 3.56 1 6.00 1c2.43 0 4.45 1.56 5.01 3.62a.5.5 0 00.96-.26C11.29 1.83 8.85 0 6.00 0 3.14 0 .70 1.83.01 4.36a.5.5 0 10.96.26z"/>
|
||||
<path fill="@image.color2" d="M3 5a3 3 0 116 0 3 3 0 01-6 0z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@restore_previous_versions='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M16 8C16 8.73 15.9 9.44 15.7 10.1C15.7 10.1 15.5 10.8 15.2 11.4C15.2 11.4 14.9 12 14.6 12.6C14.6 12.6 14.1 13.2 13.7 13.6C13.7 13.6 13.2 14.1 12.6 14.5C12.6 14.5 12 14.9 11.5 15.2C11.5 15.2 10.8 15.5 10.1 15.7C10.1 15.7 9.45 15.9 8.74 16C7.27 16 6.57 15.9 5.88 15.7C5.88 15.7 5.2 15.5 4.56 15.2C4.56 15.2 3.97 14.9 3.38 14.5C3.38 14.5 2.84 14.1 2.35 13.6C2.35 13.6 1.87 13.2 1.45 12.6C1.45 12.6 1.1 12 0.753 11.4C0.753 11.4 0.482 10.8 0.289 10.1C0.289 10.1 0.096 9.44 0 8.73C0 7.87 0.049 7.75 0.148 7.65C0.148 7.65 0.247 7.55 0.365 7.5C0.635 7.5 0.753 7.55 0.852 7.65C0.852 7.65 0.951 7.75 1 7.87C1 8.85 1.15 9.68 1.45 10.5C1.45 10.5 1.76 11.3 2.19 12C3.07 13 3.44 13.3 3.84 13.6C3.84 13.6 4.24 13.9 4.66 14.2C4.66 14.2 5.11 14.4 5.56 14.6C5.56 14.6 6.02 14.7 6.51 14.8C6.51 14.8 6.99 14.9 7.48 15C8.63 15 9.25 14.9 9.85 14.7C9.85 14.7 10.5 14.6 11 14.3C11 14.3 11.5 14 12.1 13.7C12.1 13.7 12.5 13.4 12.9 12.9C12.9 12.9 13.4 12.5 13.7 12.1C13.7 12.1 14 11.5 14.3 11C14.3 11 14.6 10.5 14.8 9.86C14.8 9.86 14.9 9.27 15 8.65C15 7.35 14.9 6.73 14.8 6.13C14.8 6.13 14.6 5.53 14.3 4.98C14.3 4.98 14 4.46 13.7 3.95C13.7 3.95 13.4 3.47 12.9 3.05C12.9 3.05 12.5 2.62 12.1 2.25C12.1 2.25 11.5 1.95 11 1.65C11 1.65 10.5 1.42 9.86 1.25C9.86 1.25 9.27 1.08 8.65 1C7.43 1 6.87 1.07 6.32 1.2C6.32 1.2 5.77 1.34 5.25 1.54C5.25 1.54 4.76 1.8 4.26 2.06C4.26 2.06 3.81 2.37 3.38 2.74C3.38 2.74 2.96 3.11 2.59 3.53L5.5 4C5.63 4 5.75 4.05 5.85 4.15C5.85 4.15 5.95 4.25 6 4.37C6 4.63 5.95 4.75 5.85 4.85C5.85 4.85 5.75 4.95 5.63 5L1.5 5C1.4 5 1.31 4.98 1.24 4.93C1.24 4.93 1.17 4.88 1.12 4.83C1.12 4.83 1.09 4.76 1.05 4.69C1.05 4.69 1.03 4.61 1.02 4.52C1.02 4.52 1.01 4.44 1 4.35C1 3.63 1 3 1 2.38C1 2.38 1 1.75 1 1.12C1 0.365 1.05 0.247 1.15 0.148C1.15 0.148 1.25 0.049 1.36 0C1.64 0 1.75 0.049 1.85 0.148C1.85 0.148 1.95 0.247 2 0.365L2 2.7C2.39 2.28 2.81 1.89 3.26 1.55C3.26 1.55 3.71 1.22 4.19 0.932C4.19 0.932 4.7 0.703 5.21 0.474C5.21 0.474 5.75 0.299 6.3 0.18C6.3 0.18 6.86 0.06 7.43 0C8.73 0 9.44 0.094 10.1 0.281C10.1 0.281 10.8 0.469 11.4 0.737C11.4 0.737 12 1.09 12.6 1.44C12.6 1.44 13.2 1.85 13.7 2.34C13.7 2.34 14.1 2.82 14.6 3.36C14.6 3.36 14.9 3.95 15.2 4.55C15.2 4.55 15.5 5.19 15.7 5.87C15.7 5.87 15.9 6.55 16 7.26Z"/>
|
||||
<path fill="@image.color2" d="M8 7.297L10.86 10.14C10.95 10.24 11 10.36 11 10.5C11 10.64 10.95 10.75 10.85 10.85C10.85 10.85 10.75 10.95 10.64 11C10.36 11 10.25 10.95 10.16 10.84L7.156 7.844C7.052 7.75 7 7.635 7 7.5L7 3.5C7 3.365 7.05 3.247 7.148 3.148C7.148 3.148 7.247 3.05 7.365 3C7.635 3 7.753 3.05 7.852 3.148C7.852 3.148 7.951 3.247 8 3.365Z"/>
|
||||
</svg>'
|
||||
|
||||
@create_shortcut, create_shortcuts_here='
|
||||
<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M4.5 12C3.9 12 3.3 12 2.8 12C2.8 12 2.2 11 1.7 11C1.7 11 1.3 11 0.92 10C0.92 10 0.6 9.8 0.36 9.2C0.36 9.2 0.12 8.7 0 8.1C0 6.9 0.12 6.3 0.36 5.7C0.36 5.7 0.6 5.2 0.92 4.7C0.92 4.7 1.3 4.3 1.7 3.9C1.7 3.9 2.2 3.6 2.8 3.4C2.8 3.4 3.3 3.1 3.9 3L6.5 3C6.6 3 6.8 3.1 6.9 3.1C6.9 3.1 7 3.2 7 3.4C7 3.6 7 3.8 6.9 3.9C6.9 3.9 6.8 4 6.6 4L4.5 4C4 4 3.6 4.1 3.1 4.3C3.1 4.3 2.7 4.5 2.3 4.7C2.3 4.7 2 5 1.7 5.3C1.7 5.3 1.5 5.7 1.3 6.1C1.3 6.1 1.1 6.5 1 7C1 8 1.1 8.4 1.3 8.9C1.3 8.9 1.5 9.3 1.7 9.7C1.7 9.7 2 10 2.3 10C2.3 10 2.7 11 3.1 11C3.1 11 3.6 11 4 11L6.5 11C6.6 11 6.8 11 6.9 11C6.9 11 7 11 7 11C7 12 7 12 6.9 12C6.9 12 6.8 12 6.6 12ZM9.5 12C9.4 12 9.2 12 9.2 12C9.2 12 9.1 12 9 12C9 11 9.1 11 9.2 11C9.2 11 9.2 11 9.4 11L12 11C12 11 12 11 13 11C13 11 13 11 14 10C14 10 14 10 14 9.7C14 9.7 15 9.3 15 8.9C15 8.9 15 8.4 15 8C15 7 15 6.5 15 6.1C15 6.1 15 5.7 14 5.3C14 5.3 14 5 14 4.7C14 4.7 13 4.5 13 4.3C13 4.3 12 4.1 12 4L9.5 4C9.4 4 9.2 4 9.2 3.9C9.2 3.9 9.1 3.8 9 3.6C9 3.4 9.1 3.2 9.2 3.1C9.2 3.1 9.2 3.1 9.4 3L12 3C12 3 13 3.1 13 3.4C13 3.4 14 3.6 14 3.9C14 3.9 15 4.3 15 4.7C15 4.7 15 5.2 16 5.7C16 5.7 16 6.3 16 6.9C16 8.1 16 8.7 16 9.2C16 9.2 15 9.8 15 10C15 10 15 11 14 11C14 11 14 11 13 12C13 12 13 12 12 12Z"/>
|
||||
<path fill="@image.color2" d="M4.5 8C4.3 8 4.2 8 4.1 7.8C4.1 7.8 4 7.7 4 7.6C4 7.4 4 7.3 4.1 7.2C4.1 7.2 4.2 7 4.3 7L12 7C12 7 12 7 12 7.2C12 7.2 12 7.3 12 7.4C12 7.6 12 7.7 12 7.8C12 7.8 12 8 12 8Z"/>
|
||||
</svg>'
|
||||
|
||||
@turn_on_bitlocker, turn_off_bitlocker='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" fill-rule="evenodd" d="M.5 9h5.49a1 1 0 001-1V5.5H14A1.5 1.5 0 0115.5 7v2a1.5 1.5 0 01-1.5 1.5H2A1.5 1.5 0 01.5 9z" clip-rule="evenodd"/>
|
||||
<path fill="@image.color1" fill-rule="evenodd" d="M0 9a2 2 0 002 2h12a2 2 0 002-2V7a2 2 0 00-2-2H6.99v1H14a1 1 0 011 1v2a1 1 0 01-1 1H2a1 1 0 01-1-1H0z" clip-rule="evenodd"/>
|
||||
<path fill="@image.color1" d="M13 7.75a.75.75 0 11-1.5 0 .75.75 0 011.5 0z"/>
|
||||
<path fill="@image.color2" fill-rule="evenodd" d="M2.99 1a1 1 0 00-1 1v1.5h-1V2a2 2 0 114 0v1.5h-1V2a1 1 0 00-1-1z" clip-rule="evenodd"/>
|
||||
<path fill="@image.color2" fill-rule="evenodd" d="M-.00 7.5v-4a.49.49 0 01.5-.5h5a.49.49 0 01.5.5v4a.49.49 0 01-.5.5h-5a.49.49 0 01-.5-.5zm4-2a1 1 0 11-2 0 1 1 0 012 0z" clip-rule="evenodd"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@show_file_extensions='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M2.5 14V2A1.5 1.5 0 014 .5h3.87a1.5 1.5 0 011.06.44l4.12 4.12a1.5 1.5 0 01.43 1.06V14a1.5 1.5 0 01-1.5 1.5H4A1.5 1.5 0 012.5 14z"/>
|
||||
<path fill="@image.color1" d="M4 1a1 1 0 00-1 1v12a1 1 0 001 1h8a1 1 0 001-1V6.12a1 1 0 00-.29-.70L8.58 1.29A1 1 0 007.87 1H4zM2 2a2 2 0 012-2h3.87a2 2 0 011.41.58l4.12 4.12A2 2 0 0114 6.12V14a2 2 0 01-2 2H4a2 2 0 01-2-2V2z"/>
|
||||
<path fill="@image.color1" d="M8 4V.5h1V4a1 1 0 001 1h3.5v1H10a2 2 0 01-2-2z"/>
|
||||
<path fill="@image.color2" d="M4 6.5a.5.5 0 01.5-.5h2a.5.5 0 010 1H6v6h.5a.5.5 0 010 1h-2a.5.5 0 010-1H5V7h-.5a.5.5 0 01-.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@show_hidden_files='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M11 9.5a3 3 0 11-6 0 3 3 0 016 0z"/>
|
||||
<path fill="@image.color2" d="M8 7a2.5 2.5 0 100 5 2.5 2.5 0 000-5zM4.5 9.5a3.5 3.5 0 117 0 3.5 3.5 0 01-7 0z"/>
|
||||
<path fill="@image.color1" d="M8 4C4.75 4 2 6.37 1.22 9.62a.5.5 0 01-.97-.23C1.12 5.74 4.24 3 8 3c3.75 0 6.87 2.73 7.75 6.38a.5.5 0 01-.97.23C13.99 6.36 11.23 4 8 4z"/>
|
||||
</svg>'
|
||||
|
||||
@compressed='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M5.5 1.5h-3a2 2 0 00-2 2v9a2 2 0 002 2h11a2 2 0 002-2v-7a2 2 0 00-2-2H8.75a1.5 1.5 0 01-1.2-.6l-.45-.6a2 2 0 00-1.6-.8z"/>
|
||||
<path fill="@image.color1" d="M2.5 1A2.5 2.5 0 000 3.5v9A2.5 2.5 0 002.5 15h11a2.5 2.5 0 002.5-2.5v-7A2.5 2.5 0 0013.5 3H8.25L7.5 2a2.5 2.5 0 00-2-1h-3zM1 3.5A1.5 1.5 0 012.5 2h3a1.5 1.5 0 011.2.6l.58.77-.55.37A1.5 1.5 0 015.89 4H1v-.5zM1 5h4.89a2.5 2.5 0 001.38-.42l.87-.58H13.5A1.5 1.5 0 0115 5.5v7a1.5 1.5 0 01-1.5 1.5h-11A1.5 1.5 0 011 12.5V5z"/>
|
||||
<path fill="@image.color2" d="M10 4a1 1 0 011-1h1a1 1 0 011 1v2a1 1 0 01-1 1v3h.5a.5.5 0 010 1H12v3.5a.5.5 0 01-1 0V13h-.5a.5.5 0 010-1h.5V9h-.5a.5.5 0 010-1h.5V7a1 1 0 01-1-1V4zm2 0h-1v2h1V4z"/>
|
||||
</svg>'
|
||||
|
||||
@more_options='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M5 8.5H1.5V12A2.5 2.5 0 004 14.5h3.5V11A2.5 2.5 0 005 8.5z"/>
|
||||
<path fill="@image.color1" d="M2 4a2 2 0 012-2h2.5a.5.5 0 000-1H4a3 3 0 00-3 3v8a3 3 0 003 3h8a3 3 0 003-3V9.5a.5.5 0 00-1 0V12a2 2 0 01-2 2H8v-3a3 3 0 00-3-3H2V4zm0 5h3a2 2 0 012 2v3H4a2 2 0 01-2-2V9z"/>
|
||||
<path fill="@image.color2" d="M9.5 1a.5.5 0 000 1h3.79L9.14 6.14a.5.5 0 10.70.70L14 2.70V6.5a.5.5 0 001 0v-5a.5.5 0 00-.5-.5h-5z"/>
|
||||
</svg>'
|
||||
|
||||
@burn_disc_image='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M8 15.5a7.5 7.5 0 100-15 7.5 7.5 0 000 15zm0-6a1.5 1.5 0 110-3 1.5 1.5 0 010 3z"/>
|
||||
<path fill="@image.color1" d="M8 1a7 7 0 100 14A7 7 0 008 1zM0 8a8 8 0 1116 0A8 8 0 010 8zm8-1a1 1 0 100 2 1 1 0 000-2zM6 8a2 2 0 114 0 2 2 0 01-4 0z"/>
|
||||
<path fill="@image.color2" d="M9.5 3.5a1.5 1.5 0 11-3 0 1.5 1.5 0 013 0z"/>
|
||||
<path fill="@image.color2" d="M8 4a4 4 0 104 4 .5.5 0 011 0 5 5 0 11-5-5 .5.5 0 010 1z"/>
|
||||
</svg>'
|
||||
|
||||
@cleanup='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@image.color1" d="M15.85.14a.5.5 0 010 .70l-5.5 5.5a.5.5 0 01-.70-.70l5.5-5.5a.5.5 0 01.70 0z"/>
|
||||
<path fill="@color3" d="M9.06 12.06l.02-.04A3.75 3.75 0 103.98 6.91l-.04.02 5.12 5.12z"/>
|
||||
<path fill="@image.color1" d="M3.60 6.56a4.25 4.25 0 115.83 5.83.5.5 0 01-.72.02L3.58 7.29a.5.5 0 01.02-.72zm.98.31l4.52 4.52A3.25 3.25 0 104.59 6.88z"/>
|
||||
<path fill="@color3" d="M9.06 12.06L3.93 6.93.5 9 7 15.5l2.06-3.43z"/>
|
||||
<path fill="@image.color2" d="M3.68 6.50a.5.5 0 01.61.07l5.12 5.12a.5.5 0 01.07.61L7.43 15.75a.5.5 0 01-.78.09l-6.5-6.5a.5.5 0 01.09-.78L3.68 6.51zm-2.37 2.59l5.59 5.59 1.53-2.55L3.86 7.56 1.30 9.1z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@move, move_to, move_here,move_to_folder, extract_all, extract_to='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@if(theme.islight,'#fff','none')" d="M2.5 1.5h3a2 2 0 011.6.8L8 3.5h4.5a2 2 0 012 2 .87.87 0 01.86.99l-.09.66A5.75 5.75 0 006.59 14.5H2.5a2 2 0 01-2-2v-9a2 2 0 012-2z"/>
|
||||
<path fill="@image.color1" d="M2.5 1A2.5 2.5 0 000 3.5v9A2.5 2.5 0 002.5 15h4.43a5.75 5.75 0 01-.61-1H2.5c-.25 0-.49-.06-.70-.17l1.44-7.02A1 1 0 014.22 6h5.59a5.75 5.75 0 011.68-.25c.58 0 1.15.08 1.68.25h.59a1 1 0 01.97.75c.35.24.67.52.96.83l.04-.31a1.99 1.99 0 00-.76-1.86A2.5 2.5 0 0012.5 3H8.25L7.5 2a2.5 2.5 0 00-2-1h-3zm10 3a1.5 1.5 0 011.41 1.00A2.04 2.04 0 0013.77 5H4.22a2 2 0 00-1.96 1.59l-1.25 6.08c-.00-.06-.01-.12-.01-.18v-9A1.5 1.5 0 012.5 2h3a1.5 1.5 0 011.2.6l.9 1.2.15.2h4.75z"/>
|
||||
<path fill="@image.color2" d="M11.5 7a4.5 4.5 0 110 9 4.5 4.5 0 010-9z"/>
|
||||
<path fill="@if(theme.islight,'#fff','#000')" d="M11.14 13.85a.5.5 0 010-.70l1.64-1.64-1.64-1.64a.5.5 0 01.70-.70l2 2a.5.5 0 010 .70l-2 2a.5.5 0 01-.70 0z"/>
|
||||
<path fill="@if(theme.islight,'#fff','#000')" d="M9 11.5a.5.5 0 01.5-.5h4a.5.5 0 010 1h-4a.5.5 0 01-.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@copy_to,copy_to_folder,copy_here='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color2" d="M0 4.5C0 3.9 0.12 3.3 0.36 2.7C0.36 2.7 0.6 2.2 0.92 1.7C0.92 1.7 1.3 1.3 1.7 0.91C1.7 0.91 2.2 0.59 2.8 0.35C2.8 0.35 3.3 0.12 3.9 0C4.9 0 5.3 0.05 5.7 0.16C5.7 0.16 6.1 0.26 6.4 0.41C6.4 0.41 6.8 0.61 7.1 0.81C7.1 0.81 7.4 1 7.7 1.3C7.7 1.3 8 1.6 8.2 1.9C8.2 1.9 8.4 2.2 8.6 2.6C8.6 2.6 8.7 2.9 8.8 3.3C8.8 3.3 9 3.7 9 4.1C9 5.1 8.9 5.7 8.7 6.2C8.7 6.2 8.4 6.8 8.1 7.3C8.1 7.3 7.7 7.7 7.3 8.1C7.3 8.1 6.8 8.4 6.3 8.6C6.3 8.6 5.7 8.9 5.1 9C3.9 9 3.3 8.9 2.7 8.7C2.7 8.7 2.2 8.4 1.7 8.1C1.7 8.1 1.3 7.7 0.91 7.3C0.91 7.3 0.59 6.8 0.35 6.3C0.35 6.3 0.12 5.7 0 5.1Z"/>
|
||||
<path fill="@image.color2" d="M8.4 12C8.2 12 7.9 12 7.6 12C7.6 12 7.4 12 7.1 12C7.1 12 6.9 11 6.7 11C6.7 11 6.5 11 6.4 11C6.4 11 6.2 11 6.1 10C6.4 9.9 6.7 9.8 7 9.7C7 9.9 7.1 10 7.2 10C7.2 10 7.3 10 7.4 10C7.4 10 7.5 11 7.6 11C7.6 11 7.8 11 8 11C8 11 8.1 11 8.3 11L12 11C13 11 13 11 13 11C13 11 13 11 13 11C13 11 14 11 14 10C14 10 14 10 14 10C14 10 14 9.9 14 9.7L14 3.5C14 3.3 14 3.1 14 2.9C14 2.9 14 2.7 14 2.6C14 2.6 14 2.4 13 2.3C13 2.3 13 2.2 13 2.1C13 2.1 13 2 13 2L9.7 2C9.6 1.8 9.5 1.7 9.4 1.5C9.4 1.5 9.3 1.3 9.2 1.2L13 1C13 1 13 1.1 13 1.2C13 1.2 14 1.3 14 1.5C14 1.5 14 1.7 14 1.9C14 1.9 15 2.2 15 2.5C15 2.5 15 2.8 15 3.1L15 9.6C15 9.9 15 10 15 10C15 10 15 11 14 11C14 11 14 11 14 11C14 11 14 12 13 12C13 12 13 12 13 12Z"/>
|
||||
<path fill="@if(theme.islight,'#fff','#000')" d="M4.5 7.1C4.7 7.1 4.8 7 4.9 6.9L6.9 4.9C7 4.8 7.1 4.7 7.1 4.5C7.1 4.3 7 4.2 6.9 4.1L4.9 2.1C4.8 2 4.7 1.9 4.5 1.9C4.3 1.9 4.2 2 4.1 2.1C4.1 2.1 4 2.2 3.9 2.3C3.9 2.7 4 2.8 4.1 2.9L5.2 4L2.5 4C2.4 4 2.2 4 2.1 4.2C2.1 4.2 2 4.2 2 4.4C2 4.6 2 4.8 2.1 4.9C2.1 4.9 2.2 5 2.4 5L5.2 5L4.1 6.1C4 6.2 3.9 6.3 3.9 6.5C3.9 6.7 4 6.8 4.1 6.9C4.1 6.9 4.2 7 4.3 7.1Z"/>
|
||||
<path fill="@image.color1" d="M3.5 15C3.1 15 2.8 15 2.5 15C2.5 15 2.2 15 1.9 14C1.9 14 1.7 14 1.5 14C1.5 14 1.3 14 1.2 13C1.2 13 1.1 13 1 13L1 9.1C1.2 9.2 1.3 9.3 1.5 9.4C1.5 9.4 1.7 9.5 1.8 9.6L2 12C2 13 2 13 2.1 13C2.1 13 2.2 13 2.3 13C2.3 13 2.5 14 2.6 14C2.6 14 2.8 14 2.9 14C2.9 14 3.1 14 3.3 14L7.5 14C7.7 14 7.8 14 8 14C8 14 8.1 14 8.2 14C8.2 14 8.4 14 8.5 14C8.5 14 8.6 14 8.7 13C8.7 13 8.8 13 8.9 13L10 13C9.9 13 9.8 14 9.6 14C9.6 14 9.5 14 9.3 14C9.3 14 9.1 14 8.9 15C8.9 15 8.6 15 8.3 15C8.3 15 8.1 15 7.8 15Z"/>
|
||||
</svg>'
|
||||
|
||||
@pc,this_pc='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M2.5 15C2.3 15 2.1 15 1.9 15C1.9 15 1.8 15 1.6 15C1.6 15 1.4 15 1.3 14C1.3 14 1.2 14 1.1 14C1.1 14 1 14 1 14L1 2.5C1 2.3 1 2.1 1.1 1.9C1.1 1.9 1.2 1.7 1.3 1.6C1.3 1.6 1.4 1.4 1.6 1.3C1.6 1.3 1.8 1.2 1.9 1.1C1.9 1.1 2.1 1 2.3 1L7.5 1C7.7 1 7.9 1 8.1 1.1C8.1 1.1 8.3 1.2 8.4 1.3C8.4 1.3 8.6 1.4 8.7 1.6C8.7 1.6 8.8 1.7 8.9 1.9C8.9 1.9 9 2.1 9 2.3L9 4L8 4L8 2.5C8 2.4 8 2.2 7.9 2.1C7.9 2.1 7.8 2 7.6 2L2.5 2C2.4 2 2.2 2 2.1 2.1C2.1 2.1 2 2.2 2 2.4L2 14C2 14 2 14 2.1 14C2.1 14 2.2 14 2.4 14L7 14L7 15Z"/>
|
||||
<path fill="@image.color1" d="M8.5 15C8.4 15 8.2 15 8.2 15C8.2 15 8.1 15 8 15C8 14 8 14 8.1 14C8.1 14 8.1 14 8.2 14C8.2 14 8.2 14 8.3 14C8.3 14 8.4 14 8.5 14C8.5 14 8.6 14 8.7 14L9 14L9 13L7.5 13C7.3 13 7.1 13 6.9 13C6.9 13 6.8 13 6.6 13C6.6 13 6.5 13 6.3 12C6.3 12 6.2 12 6.1 12C6.1 12 6 12 6 12L6 6.5C6 6.3 6 6.1 6.1 5.9C6.1 5.9 6.2 5.7 6.3 5.6C6.3 5.6 6.5 5.4 6.6 5.3C6.6 5.3 6.8 5.2 6.9 5.1C6.9 5.1 7.1 5 7.3 5L14 5C15 5 15 5 15 5.1C15 5.1 15 5.2 15 5.3C15 5.3 16 5.4 16 5.6C16 5.6 16 5.7 16 5.9C16 5.9 16 6.1 16 6.3L16 12C16 12 16 12 16 12C16 12 16 12 16 12C16 12 16 13 15 13C15 13 15 13 15 13C15 13 15 13 15 13L13 13L13 14L13 14C13 14 13 14 14 14C14 14 14 14 14 14C14 14 14 14 14 14C14 14 14 14 14 14C14 14 14 14 14 14C14 15 14 15 14 15C14 15 14 15 14 15ZM14 12C15 12 15 12 15 12C15 12 15 12 15 12L15 6.5C15 6.4 15 6.2 15 6.2C15 6.2 15 6 15 6L7.5 6C7.4 6 7.2 6 7.2 6.2C7.2 6.2 7 6.2 7 6.4L7 12C7 12 7 12 7.2 12C7.2 12 7.2 12 7.4 12Z"/>
|
||||
<path fill="@image.color2" d="M3.5 4C3.4 4 3.2 4 3.1 3.9C3.1 3.9 3.1 3.8 3 3.6C3 3.4 3.1 3.2 3.1 3.1C3.1 3.1 3.2 3.1 3.4 3L6.5 3C6.6 3 6.8 3.1 6.9 3.1C6.9 3.1 7 3.2 7 3.4C7 3.6 7 3.8 6.9 3.9C6.9 3.9 6.8 4 6.6 4ZM3.5 6C3.4 6 3.2 6 3.1 5.9C3.1 5.9 3.1 5.8 3 5.6C3 5.4 3.1 5.2 3.1 5.2C3.1 5.2 3.2 5 3.4 5L5 5L5 6Z"/>
|
||||
<path fill="@image.color2" d="M10 13L10 14L12 14L12 13Z"/>
|
||||
</svg>'
|
||||
|
||||
@command_prompt,command_prompt_admin,open_command_prompt,open_command_window_here='<svg fill="none" viewBox="0 0 16 16">
|
||||
@svg_window_template
|
||||
<path fill="@image.color2" d="M13 11.5C13 11.64 12.95 11.75 12.85 11.85C12.85 11.85 12.75 11.95 12.64 12C12.42 12 12.33 11.97 12.25 11.92C12.25 11.92 12.17 11.87 12.1 11.8L10.06 7.719C10.02 7.646 10 7.573 10 7.5C10 7.365 10.05 7.247 10.15 7.148C10.15 7.148 10.25 7.05 10.36 7C10.59 7 10.68 7.023 10.77 7.07C10.77 7.07 10.85 7.117 10.91 7.182L12.95 11.27C12.98 11.34 13 11.42 13 11.5ZM3.938 9.344C3.938 9.531 3.948 9.727 3.969 9.93C3.969 9.93 3.99 10.13 4.037 10.32C4.037 10.32 4.109 10.49 4.182 10.66C4.182 10.66 4.292 10.8 4.438 10.91C4.438 10.91 4.583 11.01 4.781 11.06C5.177 11.06 5.294 11.04 5.383 11.01C5.383 11.01 5.471 10.97 5.547 10.92C5.547 10.92 5.609 10.87 5.672 10.81C5.672 10.81 5.727 10.74 5.773 10.67C5.773 10.67 5.82 10.6 5.865 10.53C5.865 10.53 5.906 10.48 5.948 10.42C5.948 10.42 5.997 10.37 6.055 10.34C6.055 10.34 6.112 10.3 6.188 10.28C6.417 10.28 6.529 10.33 6.617 10.41C6.617 10.41 6.706 10.5 6.75 10.61C6.75 10.81 6.734 10.88 6.703 10.94C6.557 11.29 6.333 11.56 6.031 11.73C6.031 11.73 5.729 11.91 5.391 12C4.599 12 4.232 11.89 3.914 11.68C3.914 11.68 3.596 11.47 3.365 11.17C3.115 10.52 3.052 10.27 3.031 10.02C3.031 10.02 3.01 9.766 3 9.505C3 9.068 3.021 8.898 3.062 8.727C3.062 8.727 3.104 8.555 3.151 8.391C3.349 7.849 3.565 7.547 3.852 7.328C3.852 7.328 4.138 7.109 4.49 7C5.365 7 5.747 7.102 6.055 7.305C6.055 7.305 6.362 7.508 6.583 7.833C6.74 8.323 6.75 8.375 6.75 8.438C6.75 8.562 6.706 8.672 6.617 8.766C6.617 8.766 6.529 8.859 6.417 8.906C6.146 8.906 6.044 8.87 5.977 8.797C5.977 8.797 5.909 8.724 5.852 8.638C5.852 8.638 5.805 8.539 5.758 8.44C5.758 8.44 5.708 8.338 5.656 8.234C5.656 8.234 5.604 8.13 5.526 8.052C5.349 7.969 5.273 7.951 5.195 7.945C5.195 7.945 5.117 7.94 5.042 7.938L4.875 7.938C4.698 7.938 4.55 7.982 4.43 8.07C4.43 8.07 4.31 8.159 4.213 8.273C4.213 8.273 4.141 8.414 4.068 8.555C4.068 8.555 4.016 8.708 3.984 8.875C3.984 8.875 3.953 9.042 3.938 9.198ZM9 8.5C9 8.635 8.95 8.753 8.852 8.852C8.852 8.852 8.753 8.95 8.635 9C8.365 9 8.247 8.95 8.148 8.852C8.148 8.852 8.05 8.753 8 8.635C8 8.365 8.05 8.247 8.148 8.148C8.148 8.148 8.247 8.05 8.365 8C8.635 8 8.753 8.05 8.852 8.148C8.852 8.148 8.95 8.247 9 8.365ZM9 10.5C9 10.64 8.95 10.75 8.852 10.85C8.852 10.85 8.753 10.95 8.635 11C8.365 11 8.247 10.95 8.148 10.85C8.148 10.85 8.05 10.75 8 10.64C8 10.36 8.05 10.25 8.148 10.15C8.148 10.15 8.247 10.05 8.365 10C8.635 10 8.753 10.05 8.852 10.15C8.852 10.15 8.95 10.25 9 10.36Z"/>
|
||||
</svg>'
|
||||
|
||||
@manage='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M6 14L6 14C6 14 6 15 6 15C6 15 6 15 6 15L3.9 15C3.6 15 3.2 15 2.8 15C2.8 15 2.5 15 2.1 14C2.1 14 1.9 14 1.6 14C1.6 14 1.4 14 1.2 13C1.2 13 1.1 13 1 12L1 3.9C1 3.5 1.1 3.2 1.2 2.8C1.2 2.8 1.4 2.5 1.6 2.1C1.6 2.1 1.9 1.9 2.1 1.6C2.1 1.6 2.5 1.4 2.8 1.2C2.8 1.2 3.2 1.1 3.6 1L12 1C12 1 13 1.1 13 1.2C13 1.2 14 1.4 14 1.6C14 1.6 14 1.9 14 2.1C14 2.1 15 2.5 15 2.8C15 2.8 15 3.2 15 3.5L15 8.1L15 8C15 7.7 15 7.5 15 7.2C15 7.2 14 6.9 14 6.7L14 5L2 5L2 12C2 12 2 13 2.2 13C2.2 13 2.3 13 2.4 13C2.4 13 2.6 13 2.8 14C2.8 14 3 14 3.2 14C3.2 14 3.5 14 3.7 14ZM4 2C3.7 2 3.4 2 3.2 2.2C3.2 2.2 3 2.3 2.8 2.4C2.8 2.4 2.6 2.6 2.4 2.8C2.4 2.8 2.3 3 2.2 3.2C2.2 3.2 2 3.5 2 3.7L14 4L14 4C14 3.7 14 3.5 14 3.2C14 3.2 14 3 14 2.8C14 2.8 13 2.6 13 2.4C13 2.4 13 2.3 13 2.2C13 2.2 13 2 12 2Z"/>
|
||||
<path fill="@image.color2" d="M16 10L16 12L14 12L14 12C14 12 14 12 14 11C14 11 14 11 14 11C14 11 14 11 14 11C14 11 14 11 14 11C14 11 14 11 14 11C13 11 13 11 13 11C13 11 13 11 13 11C13 11 13 11 13 11C13 11 13 11 13 11C13 11 13 12 13 12L13 12L10 12L10 12C10 12 10 12 10 11C10 11 10 11 10 11C10 11 9.9 11 9.9 11C9.9 11 9.8 11 9.8 11C9.8 11 9.7 11 9.6 11C9.4 11 9.3 11 9.2 11C9.2 11 9.2 11 9.1 11C9.1 11 9.1 11 9.1 11C9.1 11 9 11 9 11C9 11 9 12 9 12L9 12L7 12L7 10C7 10 7 10 7.1 9.9C7.1 9.9 7.2 9.7 7.3 9.6C7.3 9.6 7.4 9.4 7.6 9.3C7.6 9.3 7.7 9.2 7.9 9.1C7.9 9.1 8.1 9 8.3 9L9 9L9 8.5C9 8.3 9 8.1 9.1 7.9C9.1 7.9 9.2 7.7 9.3 7.6C9.3 7.6 9.4 7.4 9.6 7.3C9.6 7.3 9.7 7.2 9.9 7.1C9.9 7.1 10 7 10 7L12 7C13 7 13 7 13 7.1C13 7.1 13 7.2 13 7.3C13 7.3 14 7.4 14 7.6C14 7.6 14 7.7 14 7.9C14 7.9 14 8.1 14 8.3L14 9L14 9C15 9 15 9 15 9.1C15 9.1 15 9.2 15 9.3C15 9.3 16 9.4 16 9.6C16 9.6 16 9.7 16 9.9C16 9.9 16 10 16 10ZM13 9L13 8.5C13 8.4 13 8.2 13 8.2C13 8.2 13 8.1 13 8L10 8C10 8 10 8.1 10 8.2C10 8.2 10 8.2 10 8.4L10 9ZM14 13L16 13L16 14C16 15 16 15 16 15C16 15 16 15 16 15C16 15 16 16 15 16C15 16 15 16 15 16C15 16 15 16 15 16L8.5 16C8.3 16 8.1 16 7.9 16C7.9 16 7.7 16 7.6 16C7.6 16 7.4 16 7.3 15C7.3 15 7.2 15 7.1 15C7.1 15 7 15 7 15L7 13L9 13L9 13C9 13 9 13 9 14C9 14 9 14 9.1 14C9.1 14 9.1 14 9.1 14C9.1 14 9.2 14 9.2 14C9.2 14 9.3 14 9.4 14C9.6 14 9.7 14 9.8 14C9.8 14 9.8 14 9.9 14C9.9 14 9.9 14 10 14C10 14 10 14 10 14C10 14 10 13 10 13L10 13L13 13L13 13C13 13 13 13 13 14C13 14 13 14 13 14C13 14 13 14 13 14C13 14 13 14 13 14C13 14 13 14 13 14C14 14 14 14 14 14C14 14 14 14 14 14C14 14 14 14 14 14C14 14 14 14 14 14C14 14 14 13 14 13Z"/>
|
||||
</svg>'
|
||||
|
||||
@edit='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M15.95 2.56C15.95 2.94 15.88 3.3 15.74 3.66C15.74 3.66 15.6 4.01 15.4 4.32L5.14 14.56C5.08 14.63 5.01 14.68 4.93 14.72C4.93 14.72 4.85 14.76 4.77 14.8L0.81 15.8C0.76 15.81 0.72 15.81 0.69 15.81C0.55 15.81 0.43 15.76 0.34 15.66C0.34 15.66 0.24 15.57 0.19 15.45C0.19 15.28 0.19 15.24 0.2 15.19L1.17 11.33C1.2 11.23 1.24 11.15 1.28 11.07C1.28 11.07 1.32 10.99 1.38 10.92L11.53 0.77C11.77 0.52 12.05 0.33 12.38 0.2C12.38 0.2 12.71 0.07 13.05 0C13.74 0 14.08 0.07 14.39 0.2C14.39 0.2 14.7 0.33 14.98 0.51C14.98 0.51 15.21 0.74 15.45 0.98C15.45 0.98 15.63 1.25 15.76 1.56C15.76 1.56 15.89 1.88 15.95 2.21ZM14.95 2.59C14.95 2.38 14.91 2.17 14.84 1.97C14.84 1.97 14.76 1.77 14.65 1.6C14.65 1.6 14.52 1.45 14.38 1.31C14.38 1.31 14.22 1.2 14.02 1.12C14.02 1.12 13.83 1.04 13.62 1C13.19 1 13.02 1.03 12.87 1.08C12.87 1.08 12.72 1.13 12.58 1.2C12.58 1.2 12.45 1.3 12.32 1.39C12.32 1.39 12.19 1.5 12.08 1.62C12.08 1.62 11.96 1.74 11.84 1.86L14 4.28C14.14 4.16 14.26 4.03 14.38 3.91C14.38 3.91 14.49 3.79 14.59 3.67C14.59 3.67 14.67 3.54 14.76 3.41C14.76 3.41 14.82 3.27 14.88 3.12C14.88 3.12 14.93 2.97 14.95 2.79ZM1.38 14.63L4.44 13.86L13.3 4.98L11.02 2.7L2.14 11.56Z"/>
|
||||
</svg>'
|
||||
|
||||
@troubleshoot_compatibility='<svg fill="none" viewBox="0 0 16 16">
|
||||
@svg_window_template2
|
||||
<path fill="@image.color2" d="M7 11.5C7 10.88 7.12 10.29 7.359 9.742C7.359 9.742 7.599 9.195 7.922 8.719C7.922 8.719 8.328 8.312 8.734 7.906C8.734 7.906 9.211 7.586 9.758 7.352C9.758 7.352 10.3 7.117 10.89 7C11.92 7 12.32 7.052 12.7 7.156C12.7 7.156 13.08 7.26 13.43 7.412C13.43 7.412 13.77 7.609 14.1 7.807C14.1 7.807 14.4 8.044 14.68 8.32C14.68 8.32 14.96 8.596 15.19 8.901C15.19 8.901 15.39 9.234 15.59 9.568C15.59 9.568 15.74 9.925 15.84 10.3C15.84 10.3 15.95 10.68 16 11.08C16 12.11 15.88 12.7 15.65 13.24C15.65 13.24 15.41 13.79 15.09 14.27C15.09 14.27 14.69 14.67 14.28 15.08C14.28 15.08 13.8 15.4 13.26 15.64C13.26 15.64 12.71 15.88 12.12 16C10.88 16 10.29 15.88 9.742 15.65C9.742 15.65 9.195 15.41 8.719 15.09C8.719 15.09 8.312 14.69 7.906 14.28C7.906 14.28 7.586 13.8 7.352 13.26C7.352 13.26 7.117 12.71 7 12.12Z"/>
|
||||
<path fill="@color_islight_WB" d="M12.12 9.5C12.12 9.323 12.07 9.175 11.95 9.055C11.95 9.055 11.83 8.935 11.68 8.875C11.33 8.875 11.19 8.935 11.06 9.055C11.06 9.055 10.94 9.175 10.88 9.323C10.88 9.667 10.94 9.812 11.06 9.938C11.06 9.938 11.19 10.06 11.33 10.12C11.68 10.12 11.83 10.06 11.95 9.938C11.95 9.938 12.07 9.812 12.12 9.667ZM12 13.5L12 11.5C12 11.36 11.95 11.25 11.85 11.15C11.85 11.15 11.75 11.05 11.64 11C11.36 11 11.25 11.05 11.15 11.15C11.15 11.15 11.05 11.25 11 11.36L11 13.5C11 13.64 11.05 13.75 11.15 13.85C11.15 13.85 11.25 13.95 11.36 14C11.64 14 11.75 13.95 11.85 13.85C11.85 13.85 11.95 13.75 12 13.64Z"/>
|
||||
</svg>'
|
||||
|
||||
@customize_this_folder='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M0 3.5C0 3.4 0.05 3.2 0.15 3.1C0.15 3.1 0.25 3.1 0.36 3L8.1 3C8.1 2.7 8.2 2.4 8.4 2.2C8.4 2.2 8.5 1.9 8.7 1.7C8.7 1.7 8.9 1.6 9.1 1.4C9.1 1.4 9.4 1.2 9.7 1.2C9.7 1.2 9.9 1.1 10 1C11 1 11 1.1 11 1.2C11 1.2 12 1.2 12 1.4C12 1.4 12 1.6 12 1.7C12 1.7 12 1.9 13 2.2C13 2.2 13 2.4 13 2.7L16 3C16 3 16 3.1 16 3.1C16 3.1 16 3.2 16 3.4C16 3.6 16 3.8 16 3.9C16 3.9 16 4 16 4L13 4C13 4.3 13 4.5 13 4.8C13 4.8 12 5 12 5.2C12 5.2 12 5.4 12 5.6C12 5.6 12 5.7 11 5.8C11 5.8 11 6 11 6C10 6 9.9 6 9.7 5.8C9.7 5.8 9.4 5.7 9.1 5.6C9.1 5.6 8.9 5.4 8.7 5.2C8.7 5.2 8.5 5 8.4 4.8C8.4 4.8 8.2 4.5 8.1 4.3L0.5 4C0.36 4 0.25 4 0.15 3.9C0.15 3.9 0.05 3.8 0 3.6ZM16 12C16 13 16 13 16 13C16 13 16 13 16 13L8 13C7.9 13 7.8 14 7.6 14C7.6 14 7.5 14 7.3 14C7.3 14 7.1 14 6.9 15C6.9 15 6.6 15 6.3 15C6.3 15 6.1 15 5.8 15C5.2 15 4.9 15 4.7 15C4.7 15 4.4 15 4.1 15C4.1 15 3.9 14 3.7 14C3.7 14 3.5 14 3.4 14C3.4 14 3.2 14 3.1 13L0.5 13C0.36 13 0.25 13 0.15 13C0.15 13 0.05 13 0 13C0 12 0.05 12 0.15 12C0.15 12 0.25 12 0.36 12L3.1 12C3.1 12 3.2 11 3.4 11C3.4 11 3.5 11 3.7 11C3.7 11 3.9 11 4.1 10C4.1 10 4.4 10 4.7 10C4.7 10 4.9 10 5.2 10C5.8 10 6.1 10 6.3 10C6.3 10 6.6 10 6.9 10C6.9 10 7.1 11 7.3 11C7.3 11 7.5 11 7.6 11C7.6 11 7.8 11 7.9 12L16 12C16 12 16 12 16 12C16 12 16 12 16 12ZM9 3.5C9 3.7 9 3.9 9.1 4.1C9.1 4.1 9.2 4.2 9.3 4.4C9.3 4.4 9.5 4.5 9.6 4.7C9.6 4.7 9.8 4.8 9.9 4.9C9.9 4.9 10 5 10 5C11 5 11 5 11 4.9C11 4.9 11 4.8 11 4.7C11 4.7 12 4.5 12 4.4C12 4.4 12 4.2 12 4.1C12 4.1 12 3.9 12 3.7C12 3.3 12 3.1 12 2.9C12 2.9 12 2.7 12 2.6C12 2.6 12 2.4 11 2.3C11 2.3 11 2.2 11 2.1C11 2.1 11 2 11 2C10 2 10 2 9.9 2.1C9.9 2.1 9.8 2.2 9.6 2.3C9.6 2.3 9.5 2.4 9.3 2.6C9.3 2.6 9.2 2.7 9.1 2.9C9.1 2.9 9 3.1 9 3.3ZM7 12C7 12 7 12 6.9 12C6.9 12 6.8 12 6.7 12C6.7 12 6.6 11 6.4 11C6.4 11 6.3 11 6.1 11C6.1 11 5.9 11 5.7 11C5.3 11 5.1 11 4.9 11C4.9 11 4.8 11 4.6 11C4.6 11 4.5 11 4.3 12C4.3 12 4.2 12 4.1 12C4.1 12 4 12 4 12C4 13 4 13 4.1 13C4.1 13 4.2 13 4.3 13C4.3 13 4.5 14 4.6 14C4.6 14 4.8 14 4.9 14C4.9 14 5.1 14 5.3 14C5.7 14 5.9 14 6.1 14C6.1 14 6.3 14 6.4 14C6.4 14 6.6 14 6.7 13C6.7 13 6.8 13 6.9 13C6.9 13 7 13 7 13Z"/>
|
||||
</svg>'
|
||||
|
||||
@give_access_to='<svg fill="none" viewBox="0 0 20 20">
|
||||
<path fill="@image.color1" d="M 3.75 5 L 3.75 4.90 C 3.75 4.22 3.88 3.58 4.15 2.99 C 4.42 2.39 4.79 1.87 5.24 1.43 C 5.70 0.99 6.23 0.64 6.84 0.38 C 7.44 0.12 8.07 0 8.75 0 C 9.44 0 10.08 0.13 10.69 0.39 C 11.30 0.65 11.83 1.00 12.29 1.45 C 12.74 1.91 13.09 2.44 13.35 3.05 C 13.61 3.66 13.75 4.30 13.75 5 C 13.75 5.69 13.61 6.33 13.35 6.94 C 13.09 7.55 12.74 8.08 12.29 8.54 C 11.83 8.99 11.30 9.34 10.69 9.60 C 10.08 9.86 9.44 10 8.75 10 C 8.05 10 7.41 9.86 6.80 9.60 C 6.19 9.34 5.66 8.99 5.20 8.54 C 4.75 8.08 4.40 7.55 4.14 6.94 C 3.88 6.33 3.75 5.69 3.75 5 Z M 12.5 5 L 12.5 4.92 C 12.5 4.41 12.39 3.93 12.19 3.49 C 11.99 3.04 11.72 2.65 11.37 2.32 C 11.03 1.99 10.63 1.73 10.18 1.53 C 9.72 1.34 9.25 1.25 8.75 1.25 C 8.22 1.25 7.74 1.34 7.28 1.54 C 6.82 1.73 6.43 2.00 6.09 2.34 C 5.75 2.68 5.48 3.07 5.29 3.53 C 5.09 3.99 5 4.47 5 5 C 5 5.52 5.09 6.00 5.29 6.46 C 5.48 6.92 5.75 7.31 6.09 7.65 C 6.43 7.99 6.82 8.26 7.28 8.45 C 7.74 8.65 8.22 8.75 8.75 8.75 C 9.27 8.75 9.75 8.65 10.21 8.45 C 10.67 8.26 11.06 7.99 11.40 7.65 C 11.74 7.31 12.01 6.92 12.20 6.46 C 12.40 6.00 12.5 5.52 12.5 5 Z M 0 13.75 C 0 13.40 0.06 13.08 0.19 12.77 C 0.32 12.47 0.50 12.21 0.73 11.98 C 0.96 11.75 1.22 11.57 1.52 11.44 C 1.83 11.31 2.15 11.25 2.5 11.25 L 11.40 11.25 C 11.35 11.45 11.31 11.66 11.28 11.87 C 11.26 12.08 11.25 12.29 11.25 12.5 L 2.5 12.5 C 2.32 12.5 2.15 12.53 2.00 12.59 C 1.85 12.66 1.72 12.75 1.61 12.86 C 1.50 12.97 1.41 13.10 1.34 13.25 C 1.28 13.40 1.25 13.57 1.25 13.75 C 1.25 14.32 1.33 14.84 1.50 15.30 C 1.68 15.76 1.91 16.17 2.21 16.52 C 2.51 16.88 2.86 17.18 3.27 17.44 C 3.67 17.70 4.10 17.91 4.57 18.09 C 5.03 18.26 5.51 18.39 6.01 18.49 C 6.51 18.59 7.01 18.66 7.5 18.70 C 7.5 18.78 7.49 18.86 7.49 18.95 C 7.49 19.03 7.49 19.11 7.49 19.20 C 7.49 19.33 7.49 19.46 7.50 19.59 C 7.52 19.72 7.55 19.84 7.59 19.96 C 6.97 19.92 6.36 19.84 5.74 19.71 C 5.13 19.59 4.54 19.42 3.97 19.19 C 3.41 18.97 2.89 18.70 2.40 18.37 C 1.92 18.04 1.50 17.65 1.14 17.21 C 0.79 16.76 0.51 16.25 0.30 15.68 C 0.10 15.11 0 14.46 0 13.75 Z "/>
|
||||
<path fill="@image.color2" d="M 9.37 20 C 9.20 20 9.05 19.93 8.93 19.81 C 8.81 19.69 8.75 19.54 8.75 19.37 L 8.75 17.5 C 8.75 17.33 8.81 17.18 8.93 17.06 L 12.60 13.38 C 12.53 13.05 12.5 12.72 12.5 12.42 C 12.5 11.91 12.60 11.43 12.80 10.99 C 13.00 10.54 13.27 10.15 13.62 9.82 C 13.96 9.49 14.36 9.23 14.81 9.03 C 15.27 8.84 15.74 8.75 16.25 8.75 C 16.77 8.75 17.25 8.84 17.71 9.04 C 18.17 9.23 18.56 9.50 18.90 9.84 C 19.24 10.18 19.51 10.57 19.70 11.03 C 19.90 11.49 20 11.97 20 12.5 C 20 13.00 19.90 13.47 19.71 13.93 C 19.51 14.38 19.25 14.78 18.92 15.12 C 18.59 15.47 18.20 15.74 17.75 15.94 C 17.31 16.14 16.83 16.25 16.32 16.25 C 16.10 16.25 15.87 16.23 15.65 16.20 C 15.43 16.16 15.21 16.11 15 16.03 C 14.99 16.10 15.00 16.18 15.00 16.27 C 15.00 16.37 15.00 16.46 15.00 16.56 C 15.00 16.67 15.00 16.79 14.99 16.90 C 14.97 17.01 14.94 17.11 14.90 17.20 C 14.85 17.29 14.79 17.36 14.70 17.41 C 14.62 17.47 14.51 17.5 14.37 17.5 L 13.75 17.5 C 13.75 17.80 13.74 18.04 13.72 18.20 C 13.70 18.37 13.66 18.49 13.57 18.57 C 13.49 18.66 13.37 18.70 13.20 18.72 C 13.03 18.74 12.79 18.75 12.5 18.75 L 12.5 19.08 C 12.5 19.19 12.49 19.30 12.48 19.40 C 12.46 19.51 12.43 19.61 12.39 19.70 C 12.35 19.79 12.29 19.86 12.21 19.91 C 12.13 19.97 12.01 20 11.87 20 Z M 18.12 11.56 C 18.12 11.30 18.03 11.08 17.85 10.89 C 17.66 10.71 17.44 10.62 17.18 10.62 C 16.92 10.62 16.70 10.71 16.52 10.89 C 16.34 11.08 16.25 11.30 16.25 11.56 C 16.25 11.82 16.34 12.04 16.52 12.22 C 16.70 12.40 16.92 12.5 17.18 12.5 C 17.44 12.5 17.66 12.40 17.85 12.22 C 18.03 12.04 18.12 11.82 18.12 11.56 Z " />
|
||||
</svg>'
|
||||
|
||||
@send_to='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M16 7.5C16 7.6 16 7.7 16 7.8C16 7.8 16 7.9 16 7.9L0.72 15C0.66 15 0.58 15 0.5 15C0.35 15 0.23 15 0.14 15C0.14 15 0.05 15 0 15C0 14 0 14 0 14C0 14 0 14 0.01 14L2 7.5L0.02 0.64C0.01 0.62 0 0.6 0 0.58C0 0.58 0 0.56 0 0.53C0 0.35 0.05 0.23 0.14 0.14C0.14 0.14 0.23 0.05 0.35 0C0.58 0 0.66 0.02 0.72 0.05L16 7C16 7.1 16 7.3 16 7.5ZM1.3 14L14 7.5L1.3 1.4L2.9 7L9.5 7C9.6 7 9.8 7 9.8 7.2C9.8 7.2 10 7.2 10 7.4C10 7.6 10 7.8 9.8 7.9C9.8 7.9 9.8 8 9.6 8L2.9 8Z"/>
|
||||
</svg>'
|
||||
|
||||
@include_in_library='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M1.5 16C1.3 16 1.1 16 0.93 16C0.93 16 0.75 16 0.59 16C0.59 16 0.45 16 0.3 15C0.3 15 0.2 15 0.12 15C0.12 15 0.04 15 0 15L0 1.5C0 1.3 0.04 1.1 0.12 0.91C0.12 0.91 0.2 0.73 0.3 0.57C0.3 0.57 0.45 0.44 0.59 0.3C0.59 0.3 0.75 0.2 0.93 0.12C0.93 0.12 1.1 0.04 1.3 0L2.5 0C2.7 0 2.9 0.04 3.1 0.12C3.1 0.12 3.3 0.2 3.4 0.3C3.4 0.3 3.6 0.44 3.7 0.57C3.7 0.57 3.8 0.73 3.9 0.91C3.9 0.91 4 1.1 4 1.3L4 14C4 15 4 15 3.9 15C3.9 15 3.8 15 3.7 15C3.7 15 3.6 16 3.4 16C3.4 16 3.3 16 3.1 16C3.1 16 2.9 16 2.7 16ZM6.5 16C6.3 16 6.1 16 5.9 16C5.9 16 5.8 16 5.6 16C5.6 16 5.5 16 5.3 15C5.3 15 5.2 15 5.1 15C5.1 15 5 15 5 15L5 1.5C5 1.3 5 1.1 5.1 0.91C5.1 0.91 5.2 0.73 5.3 0.57C5.3 0.57 5.5 0.44 5.6 0.3C5.6 0.3 5.8 0.2 5.9 0.12C5.9 0.12 6.1 0.04 6.3 0L7.5 0C7.7 0 7.9 0.04 8.1 0.12C8.1 0.12 8.3 0.2 8.4 0.3C8.4 0.3 8.6 0.44 8.7 0.57C8.7 0.57 8.8 0.73 8.9 0.91C8.9 0.91 9 1.1 9 1.3L9 14C9 15 9 15 8.9 15C8.9 15 8.8 15 8.7 15C8.7 15 8.6 16 8.4 16C8.4 16 8.3 16 8.1 16C8.1 16 7.9 16 7.7 16ZM2.5 15C2.6 15 2.8 15 2.9 15C2.9 15 3 15 3 15L3 1.5C3 1.4 3 1.2 2.9 1.2C2.9 1.2 2.8 1.1 2.6 1L1.5 1C1.4 1 1.2 1.1 1.2 1.2C1.2 1.2 1.1 1.2 1 1.4L1 14C1 15 1.1 15 1.2 15C1.2 15 1.2 15 1.4 15ZM7.5 15C7.6 15 7.8 15 7.9 15C7.9 15 8 15 8 15L8 1.5C8 1.4 8 1.2 7.9 1.2C7.9 1.2 7.8 1.1 7.6 1L6.5 1C6.4 1 6.2 1.1 6.2 1.2C6.2 1.2 6 1.2 6 1.4L6 14C6 15 6 15 6.2 15C6.2 15 6.2 15 6.4 15ZM10 4.7C10 4.4 10 4.1 10 3.8C10 3.8 11 3.5 11 3.4C11 3.2 11 3.1 12 3.1C12 3.1 12 3 12 3C12 3 13 3 13 3.1C13 3.1 13 3.1 13 3.2C13 3.2 13 3.3 13 3.4C13 3.4 13 3.6 14 3.7C14 3.7 14 3.8 14 4L16 14C16 14 16 14 16 14C16 15 16 15 16 15C16 15 15 15 15 16C15 16 14 16 14 16C14 16 14 16 14 16C13 16 13 16 13 16C13 16 13 16 13 16C13 16 13 16 12 16C12 16 12 15 12 15C12 15 12 15 12 15L10 5C10 4.9 10 4.8 10 4.7ZM15 14C15 14 15 14 15 14L13 4.4C13 4.3 13 4.2 13 4.1C13 4.1 12 4 12 4C12 4 12 4 12 4.1C12 4.1 12 4.1 12 4.2C11 4.2 11 4.3 11 4.4C11 4.4 11 4.5 11 4.6C11 4.7 11 4.7 11 4.8C11 4.8 11 4.8 11 4.8L13 15C13 15 13 15 13 15C13 15 13 15 13 15C14 15 14 15 14 15C14 15 14 15 14 15C14 15 14 15 14 15C14 15 14 15 14 15C14 15 14 15 15 15C15 15 15 15 15 15C15 15 15 14 15 14Z"/>
|
||||
</svg>'
|
||||
|
||||
@add_a_network_location='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M1.5 2.5a1 1 0 011-1h8a1 1 0 011 1v5a1 1 0 01-1 1h-8a1 1 0 01-1-1v-5z"/>
|
||||
<path fill="@image.color1" d="M1 2.5A1.5 1.5 0 012.5 1h8A1.5 1.5 0 0112 2.5v5A1.5 1.5 0 0110.5 9h-8A1.5 1.5 0 011 7.5v-5zM2.5 2a.5.5 0 00-.5.5v5a.5.5 0 00.5.5h8a.5.5 0 00.5-.5v-5a.5.5 0 00-.5-.5h-8zM7.5 10.5a.5.5 0 01.5.5v1.5a.5.5 0 01-1 0V11a.5.5 0 01.5-.5zM0 14.5a.5.5 0 01.5-.5h4a.5.5 0 010 1h-4a.5.5 0 01-.5-.5zM10 14.5a.5.5 0 01.5-.5h4a.5.5 0 010 1h-4a.5.5 0 01-.5-.5z"/>
|
||||
<path fill="@color3" d="M4.5 14a.5.5 0 01.5-.5h1.5V13a.5.5 0 01.5-.5h1a.5.5 0 01.5.5v.5H10a.5.5 0 01.5.5v1a.5.5 0 01-.5.5H5a.5.5 0 01-.5-.5v-1z"/>
|
||||
<path fill="@image.color2" d="M6 13a1 1 0 011-1h1a1 1 0 011 1h1a1 1 0 011 1v1a1 1 0 01-1 1H5a1 1 0 01-1-1v-1a1 1 0 011-1h1zm2 0H7v.5a.5.5 0 01-.5.5H5v1h5v-1H8.5a.5.5 0 01-.5-.5V13z"/>
|
||||
<path fill="@image.color1" d="M3.08 10A1.5 1.5 0 004.5 11h7A2.5 2.5 0 0014 8.5v-4a1.5 1.5 0 00-1-1.41V8.5a1.5 1.5 0 01-1.5 1.5H3.08z"/>
|
||||
</svg>'
|
||||
|
||||
@disconnect_network_drive='<svg fill="none" viewBox="0 0 16 16">
|
||||
<g clip-path="url(#clip0)">
|
||||
<path fill="@color3" d="M2.5 2.5H2A1.5 1.5 0 00.5 4v2A1.5 1.5 0 002 7.5h5.5l-5-5zM9.62 7.5H13A1.5 1.5 0 0014.5 6V4A1.5 1.5 0 0013 2.5H4.62l5 5zM4.5 12a.5.5 0 01.5-.5h1.5V11a.5.5 0 01.5-.5h1a.5.5 0 01.5.5v.5H10a.5.5 0 01.5.5v1a.5.5 0 01-.5.5H5a.5.5 0 01-.5-.5v-1z"/>
|
||||
<g>
|
||||
<path fill="@image.color1" d="M0 4a2 2 0 012-2l1 1H2a1 1 0 00-1 1v2a1 1 0 001 1h5l1 1v2a1 1 0 011 1h1a1 1 0 011 1h1l1 1h-2a1 1 0 01-1 1H5a1 1 0 01-1-1H.5a.5.5 0 010-1H4a1 1 0 011-1h1a1 1 0 011-1V8H2a2 2 0 01-2-2V4zm5 9h5v-1H8.5a.5.5 0 01-.5-.5V11H7v.5a.5.5 0 01-.5.5H5v1zM13 7H9.12l1 1H13a2 2 0 002-2V4a2 2 0 00-2-2H4.12l1 1H13a1 1 0 011 1v2a1 1 0 01-1 1z"/>
|
||||
<path fill="@image.color1" d="M11.25 5.5a.75.75 0 100-1.5.75.75 0 000 1.5z"/>
|
||||
</g>
|
||||
<path fill="@image.color2" d="M.14.14a.5.5 0 01.70 0l15 15a.5.5 0 01-.70.70l-15-15a.5.5 0 010-.70z"/>
|
||||
</g>
|
||||
@clipPath
|
||||
</svg>'
|
||||
|
||||
@map_network_drive='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M7.5 7a.5.5 0 01.5.5v3a.5.5 0 01-1 0v-3a.5.5 0 01.5-.5z"/>
|
||||
<path fill="@color3" d="M13 7.5H2A1.5 1.5 0 01.5 6V4A1.5 1.5 0 012 2.5h11A1.5 1.5 0 0114.5 4v2A1.5 1.5 0 0113 7.5z"/>
|
||||
<path fill="@image.color1" d="M0 4a2 2 0 012-2h11a2 2 0 012 2v2a2 2 0 01-2 2H2a2 2 0 01-2-2V4zm2-1a1 1 0 00-1 1v2a1 1 0 001 1h11a1 1 0 001-1V4a1 1 0 00-1-1H2z"/>
|
||||
<path fill="@image.color1" d="M12 4.75a.75.75 0 11-1.5 0 .75.75 0 011.5 0zM0 12.5a.5.5 0 01.5-.5h4a.5.5 0 010 1h-4a.5.5 0 01-.5-.5zM10 12.5a.5.5 0 01.5-.5h4a.5.5 0 010 1h-4a.5.5 0 01-.5-.5z"/>
|
||||
<path fill="@color3" d="M4.5 12a.5.5 0 01.5-.5h1.5V11a.5.5 0 01.5-.5h1a.5.5 0 01.5.5v.5H10a.5.5 0 01.5.5v1a.5.5 0 01-.5.5H5a.5.5 0 01-.5-.5v-1z"/>
|
||||
<path fill="@image.color2" d="M6 11a1 1 0 011-1h1a1 1 0 011 1h1a1 1 0 011 1v1a1 1 0 01-1 1H5a1 1 0 01-1-1v-1a1 1 0 011-1h1zm2 0H7v.5a.5.5 0 01-.5.5H5v1h5v-1H8.5a.5.5 0 01-.5-.5V11z"/>
|
||||
</svg>'
|
||||
|
||||
@make_available_offline='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M8 .5C5.72.5 3.88 2.18 3.88 4.26a.48.48 0 01-.48.48h-.02a2.87 2.87 0 100 5.75h2.46a5.75 5.75 0 019.65-3.14 2.87 2.87 0 00-2.86-2.60H12.6a.48.48 0 01-.48-.48C12.11 2.18 10.27.5 8 .5z"/>
|
||||
<path fill="@image.color1" d="M8 0C5.49 0 3.39 1.86 3.38 4.25h-.00a3.37 3.37 0 000 6.75h2.39c.03-.34.09-.67.17-1H3.37a2.37 2.37 0 110-4.75h.02c.54 0 .98-.44.98-.98C4.38 2.50 5.96 1 8 1c2.04 0 3.61 1.50 3.61 3.26 0 .54.44.98.98.98h.02c1.03 0 1.91.66 2.24 1.58.42.30.79.66 1.12 1.06a3.37 3.37 0 00-3.36-3.65h-.00C12.60 1.86 10.50 0 8 0z"/>
|
||||
<path fill="@image.color2" d="M16 11.5a4.5 4.5 0 11-9 0 4.5 4.5 0 019 0z"/>
|
||||
<path fill="@color_islight_WB" d="M9.10 11.10c.22-.22.57-.22.79 0l1.60 1.60 1.60-1.60a.56.56 0 11.79.79l-2 2a.56.56 0 01-.79 0l-2-2a.56.56 0 010-.79z"/>
|
||||
<path fill="@color_islight_WB" d="M11.5 9a.5.5 0 01.5.5v4a.5.5 0 01-1 0v-4a.5.5 0 01.5-.5z"/>
|
||||
</svg>'
|
||||
|
||||
@make_available_online='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@color3" d="M3.88 6.26C3.88 4.18 5.72 2.5 8 2.5c2.27 0 4.11 1.68 4.11 3.76 0 .26.21.48.48.48h.02a2.87 2.87 0 010 5.75h-9.25a2.87 2.87 0 010-5.75h.02a.48.48 0 00.48-.48z"/>
|
||||
<path fill="@image.color1" d="M3.38 6.25C3.39 3.86 5.49 2 8 2c2.50 0 4.60 1.86 4.61 4.25h.00a3.37 3.37 0 110 6.75h-9.25a3.37 3.37 0 110-6.75h.00zM8 3C5.95 3 4.38 4.50 4.38 6.26c0 .54-.44.98-.98.98h-.02a2.37 2.37 0 100 4.75h9.25a2.37 2.37 0 100-4.75H12.6a.98.98 0 01-.98-.98C11.61 4.50 10.04 3 8 3z"/>
|
||||
</svg>'
|
||||
|
||||
@file_explorer='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M14 3C14 3 14 3.1 14 3.2C14 3.2 15 3.3 15 3.5C15 3.5 15 3.7 16 4C16 4 16 4.2 16 4.5C16 4.5 16 4.8 16 5.1L16 13C16 13 16 13 16 13C16 13 16 14 16 14C16 14 15 14 15 14C15 14 15 15 14 15C14 15 14 15 14 15L2.5 15C2.1 15 1.8 15 1.5 15C1.5 15 1.2 15 0.95 14C0.95 14 0.73 14 0.52 14C0.52 14 0.34 14 0.2 13C0.2 13 0.07 13 0 13L0 3.4C0 3.1 0.07 2.8 0.2 2.5C0.2 2.5 0.34 2.2 0.52 1.9C0.52 1.9 0.73 1.7 0.95 1.5C0.95 1.5 1.2 1.3 1.5 1.2C1.5 1.2 1.8 1.1 2.1 1L5.5 1C5.9 1 6.3 1.1 6.6 1.3C6.6 1.3 7 1.4 7.3 1.7L8.2 3ZM1 4L5.9 4C6 4 6.2 4 6.3 4C6.3 4 6.4 3.9 6.5 3.9C6.5 3.9 6.6 3.8 6.7 3.7C6.7 3.7 6.9 3.7 7 3.6C7 3.6 7.1 3.5 7.2 3.5C7.2 3.2 7 3 6.9 2.9C6.9 2.9 6.8 2.7 6.7 2.6C6.7 2.6 6.5 2.4 6.4 2.3C6.4 2.3 6.3 2.2 6.1 2.1C6.1 2.1 5.9 2 5.7 2L2.5 2C2.3 2 2.1 2 1.9 2.1C1.9 2.1 1.8 2.2 1.6 2.3C1.6 2.3 1.4 2.4 1.3 2.6C1.3 2.6 1.2 2.7 1.1 2.9C1.1 2.9 1 3.1 1 3.3ZM15 5.5C15 5.3 15 5.1 15 4.9C15 4.9 15 4.7 15 4.6C15 4.6 15 4.4 14 4.3C14 4.3 14 4.2 14 4.1C14 4.1 14 4 14 4L8.2 4C8 4.1 7.8 4.2 7.6 4.4C7.6 4.4 7.5 4.5 7.3 4.6C7.3 4.6 7.1 4.7 6.9 4.8C6.9 4.8 6.7 4.9 6.5 4.9C6.5 4.9 6.4 5 6.1 5L1 5L1 12C1 13 1 13 1.1 13C1.1 13 1.2 13 1.3 13C1.3 13 1.4 14 1.6 14C1.6 14 1.8 14 1.9 14C1.9 14 2.1 14 2.3 14L3 14L3 10C3 10 3 10 3.1 9.9C3.1 9.9 3.2 9.7 3.3 9.6C3.3 9.6 3.5 9.4 3.6 9.3C3.6 9.3 3.8 9.2 3.9 9.1C3.9 9.1 4.1 9 4.3 9L12 9C12 9 12 9 12 9.1C12 9.1 12 9.2 12 9.3C12 9.3 13 9.4 13 9.6C13 9.6 13 9.7 13 9.9C13 9.9 13 10 13 10L13 14L14 14C14 14 14 14 14 14C14 14 14 14 14 14C14 14 15 14 15 13C15 13 15 13 15 13C15 13 15 13 15 13ZM12 14L12 10C12 10 12 10 12 10C12 10 12 10 12 10L4.5 10C4.4 10 4.2 10 4.2 10C4.2 10 4 10 4 10L4 14Z"/>
|
||||
<path fill="@image.color2" d="M10 12C11 12 11 12 11 12C11 12 11 12 11 12C11 13 11 13 11 13C11 13 11 13 11 13L5.5 13C5.4 13 5.2 13 5.2 13C5.2 13 5 13 5 13C5 12 5 12 5.2 12C5.2 12 5.2 12 5.4 12Z"/>
|
||||
</svg>'
|
||||
|
||||
@file_explorer_options='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M10.65 15.52C10.6 15.52 10.56 15.52 10.52 15.5C10.45 15.46 10.39 15.41 10.34 15.34C10.08 14.92 9.75 14.59 9.36 14.35C8.97 14.11 8.52 13.99 8.02 13.99C7.77 13.99 7.53 14.02 7.32 14.08C7.11 14.14 6.89 14.23 6.68 14.35C6.56 14.42 6.46 14.49 6.37 14.56C6.28 14.63 6.2 14.7 6.12 14.78C6.05 14.86 5.98 14.94 5.91 15.03C5.85 15.12 5.78 15.22 5.7 15.34C5.63 15.45 5.53 15.51 5.4 15.51C5.36 15.51 5.32 15.5 5.27 15.49C5.11 15.45 4.91 15.38 4.69 15.27C4.47 15.16 4.25 15.04 4.02 14.91C3.79 14.78 3.58 14.64 3.38 14.5C3.17 14.35 3.01 14.22 2.88 14.11C2.8 14.04 2.76 13.95 2.76 13.84C2.76 13.78 2.78 13.72 2.81 13.66C2.93 13.44 3.02 13.22 3.08 13.01C3.14 12.8 3.17 12.57 3.17 12.32C3.17 11.83 3.05 11.38 2.81 10.98C2.57 10.58 2.24 10.25 1.82 10.01C1.41 9.77 .96 9.65 .48 9.65C.44 9.65 .4 9.64 .36 9.63C.32 9.62 .29 9.6 .25 9.57C.19 9.52 .15 9.42 .11 9.28C.08 9.13 .05 8.98 .04 8.81C.02 8.64 .01 8.48 .01 8.32C0 8.16 0 8.04 0 7.95C0 7.73 .01 7.51 .02 7.28C.04 7.05 .07 6.83 .11 6.62C.12 6.57 .13 6.53 .15 6.5C.17 6.47 .2 6.44 .23 6.41C.28 6.37 .32 6.35 .36 6.34C.41 6.33 .46 6.33 .51 6.33C.97 6.33 1.4 6.21 1.8 5.98C2.23 5.74 2.56 5.42 2.79 5.01C3.03 4.6 3.15 4.15 3.15 3.66C3.15 3.41 3.11 3.18 3.05 2.97C2.98 2.76 2.89 2.55 2.77 2.33C2.74 2.27 2.72 2.21 2.72 2.15C2.72 2.04 2.76 1.95 2.85 1.88C3.01 1.73 3.19 1.59 3.38 1.46C3.58 1.32 3.77 1.2 3.98 1.09C4.19 .97 4.4 .87 4.61 .77C4.82 .68 5.03 .6 5.23 .52C5.27 .51 5.31 .5 5.36 .5C5.49 .5 5.59 .56 5.66 .67C5.91 1.09 6.23 1.42 6.64 1.66C7.05 1.91 7.49 2.03 7.98 2.03C8.46 2.03 8.91 1.91 9.32 1.67C9.43 1.6 9.54 1.54 9.62 1.46C9.71 1.39 9.8 1.32 9.87 1.24C9.95 1.16 10.02 1.08 10.09 .99C10.15 .9 10.22 .8 10.3 .69C10.33 .64 10.38 .59 10.43 .56C10.49 .52 10.55 .51 10.61 .51C10.65 .51 10.68 .52 10.73 .53C10.93 .6 11.14 .69 11.35 .79C11.57 .88 11.78 .99 11.98 1.11C12.19 1.22 12.39 1.35 12.59 1.48C12.78 1.62 12.96 1.76 13.12 1.91C13.2 1.98 13.24 2.07 13.24 2.19C13.24 2.23 13.24 2.26 13.23 2.29C13.22 2.31 13.21 2.34 13.19 2.37C13.07 2.59 12.98 2.8 12.92 3.01C12.86 3.22 12.83 3.45 12.83 3.7C12.83 4.19 12.95 4.63 13.19 5.04C13.43 5.45 13.76 5.78 14.18 6.02C14.59 6.25 15.04 6.37 15.52 6.37C15.6 6.37 15.68 6.4 15.75 6.45C15.79 6.48 15.81 6.51 15.83 6.54C15.85 6.58 15.86 6.61 15.88 6.66C15.93 6.89 15.96 7.12 15.98 7.36C15.99 7.61 16 7.84 16 8.08C16 8.3 15.99 8.52 15.98 8.74C15.97 8.97 15.94 9.18 15.89 9.4C15.87 9.48 15.83 9.55 15.77 9.61C15.69 9.67 15.6 9.7 15.49 9.7C15.03 9.7 14.6 9.81 14.2 10.04C13.77 10.28 13.44 10.6 13.21 11.02C12.97 11.43 12.85 11.88 12.85 12.36C12.85 12.6 12.88 12.83 12.95 13.05C13.01 13.28 13.11 13.49 13.23 13.7C13.25 13.73 13.26 13.76 13.27 13.78C13.28 13.8 13.28 13.83 13.28 13.88C13.28 13.97 13.24 14.06 13.15 14.14C12.8 14.44 12.43 14.7 12.02 14.93C11.6 15.16 11.19 15.35 10.77 15.5C10.72 15.52 10.68 15.52 10.65 15.52ZM7.99 11.99C8.54 11.99 9.07 11.89 9.55 11.68C10.04 11.46 10.47 11.18 10.83 10.81C11.19 10.45 11.48 10.02 11.69 9.54C11.9 9.05 12.01 8.53 12.01 7.97C12.01 7.42 11.9 6.9 11.69 6.42C11.47 5.94 11.19 5.52 10.82 5.16C10.46 4.8 10.04 4.51 9.55 4.31C9.06 4.1 8.55 4 8 4C7.45 4 6.94 4.1 6.45 4.31C5.97 4.52 5.55 4.81 5.18 5.17C4.82 5.53 4.54 5.95 4.32 6.44C4.11 6.92 4.01 7.44 4.01 7.98C4.01 8.54 4.11 9.06 4.32 9.54C4.53 10.03 4.81 10.45 5.17 10.82C5.53 11.18 5.95 11.46 6.44 11.68C6.92 11.89 7.44 11.99 7.99 11.99Z"/>
|
||||
<path fill="@image.color2" d="M5.34 8L5.34 7.95C5.34 7.58 5.41 7.24 5.55 6.92C5.69 6.6 5.89 6.33 6.13 6.09C6.38 5.86 6.66 5.67 6.98 5.54C7.3 5.4 7.64 5.34 8 5.34C8.37 5.34 8.72 5.4 9.04 5.54C9.37 5.68 9.65 5.87 9.89 6.11C10.13 6.35 10.32 6.63 10.46 6.96C10.6 7.28 10.66 7.63 10.66 8C10.66 8.37 10.6 8.72 10.46 9.04C10.32 9.37 10.13 9.65 9.89 9.89C9.65 10.13 9.37 10.32 9.04 10.46C8.72 10.6 8.37 10.66 8 10.66C7.63 10.66 7.28 10.6 6.96 10.46C6.63 10.32 6.35 10.13 6.11 9.89C5.87 9.65 5.68 9.37 5.54 9.04C5.4 8.72 5.34 8.37 5.34 8Z "/>
|
||||
</svg>'
|
||||
|
||||
@print='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M16 5.5L16 10C16 11 16 11 16 11C16 11 16 11 16 11C15 12 15 12 15 12C15 12 15 12 15 12L13 12L13 14C13 14 13 14 13 14C13 14 13 14 13 14C13 14 13 15 12 15C12 15 12 15 12 15C12 15 12 15 12 15L4.5 15C4.3 15 4.1 15 3.9 15C3.9 15 3.8 15 3.6 15C3.6 15 3.5 15 3.3 14C3.3 14 3.2 14 3.1 14C3.1 14 3 14 3 14L3 12L1.5 12C1.3 12 1.1 12 0.93 12C0.93 12 0.75 12 0.58 12C0.3 11 0.2 11 0.12 11C0.12 11 0.04 11 0 11L0 5.5C0 5.2 0.07 4.8 0.2 4.5C0.2 4.5 0.33 4.2 0.51 4C0.51 4 0.73 3.7 0.96 3.5C0.96 3.5 1.2 3.3 1.5 3.2C1.5 3.2 1.8 3.1 2.2 3L3 3L3 2.5C3 2.3 3 2.1 3.1 1.9C3.1 1.9 3.2 1.7 3.3 1.6C3.3 1.6 3.4 1.4 3.6 1.3C3.6 1.3 3.7 1.2 3.9 1.1C3.9 1.1 4.1 1 4.3 1L12 1C12 1 12 1 12 1.1C12 1.1 12 1.2 12 1.3C12 1.3 13 1.4 13 1.6C13 1.6 13 1.7 13 1.9C13 1.9 13 2.1 13 2.3L13 3L14 3C14 3 14 3.1 14 3.2C14 3.2 15 3.3 15 3.5C15 3.5 15 3.7 16 4C16 4 16 4.2 16 4.5C16 4.5 16 4.8 16 5.2ZM4 3L12 3L12 2.5C12 2.4 12 2.2 12 2.1C12 2.1 12 2 12 2L4.5 2C4.4 2 4.2 2 4.2 2.1C4.2 2.1 4 2.2 4 2.4ZM15 5.5C15 5.3 15 5.1 15 4.9C15 4.9 15 4.7 15 4.6C15 4.6 15 4.4 14 4.3C14 4.3 14 4.2 14 4.1C14 4.1 14 4 14 4L2.5 4C2.3 4 2.1 4 1.9 4.1C1.9 4.1 1.7 4.2 1.6 4.3C1.6 4.3 1.4 4.4 1.3 4.6C1.3 4.6 1.2 4.7 1.1 4.9C1.1 4.9 1 5.1 1 5.3L1 10C1 11 1.1 11 1.2 11C1.2 11 1.2 11 1.4 11L3 11L3 9.5C3 9.3 3 9.1 3.1 8.9C3.1 8.9 3.2 8.7 3.3 8.6C3.3 8.6 3.5 8.4 3.6 8.3C3.6 8.3 3.8 8.2 3.9 8.1C3.9 8.1 4.1 8 4.3 8L12 8C12 8 12 8 12 8.1C12 8.1 12 8.2 12 8.3C12 8.3 13 8.4 13 8.6C13 8.6 13 8.7 13 8.9C13 8.9 13 9.1 13 9.3L13 11L14 11C15 11 15 11 15 11C15 11 15 11 15 11ZM12 9.5C12 9.4 12 9.2 12 9.2C12 9.2 12 9.1 12 9L4.5 9C4.4 9 4.2 9.1 4.2 9.2C4.2 9.2 4 9.2 4 9.4L4 14C4 14 4 14 4.2 14C4.2 14 4.2 14 4.4 14L12 14C12 14 12 14 12 14C12 14 12 14 12 14Z"/>
|
||||
</svg>'
|
||||
|
||||
@device_manager='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M7 14L7 13L10 13L10 11L7 11L7 10L14 10C14.15 10 14.28 9.974 14.4 9.922C14.4 9.922 14.52 9.87 14.62 9.797C14.62 9.797 14.71 9.703 14.8 9.609C14.8 9.609 14.87 9.503 14.92 9.383C14.92 9.383 14.97 9.263 15 9.135L15 2C15 1.865 14.97 1.734 14.92 1.609C14.92 1.609 14.87 1.484 14.8 1.378C14.8 1.378 14.71 1.289 14.62 1.201C14.62 1.201 14.52 1.13 14.39 1.078C14.39 1.078 14.27 1.026 14.14 1L4 1C3.865 1 3.737 1.026 3.617 1.078C3.617 1.078 3.497 1.13 3.391 1.201C3.391 1.201 3.297 1.289 3.203 1.378C3.203 1.378 3.13 1.482 3.078 1.602C3.078 1.602 3.026 1.721 3 1.854L3 5L2 5L2 1.953C2 1.693 2.055 1.445 2.164 1.211C2.164 1.211 2.273 0.9766 2.417 0.7682C2.417 0.7682 2.594 0.5859 2.771 0.4036C2.771 0.4036 2.979 0.2604 3.219 0.1563C3.219 0.1563 3.458 0.0521 3.708 0L14.05 0C14.31 0 14.55 0.0521 14.79 0.1563C14.79 0.1563 15.02 0.2604 15.23 0.4036C15.23 0.4036 15.41 0.5859 15.6 0.7682C15.6 0.7682 15.74 0.9766 15.84 1.211C15.84 1.211 15.95 1.445 16 1.693L16 9.031C16 9.302 15.95 9.557 15.84 9.797C15.84 9.797 15.73 10.04 15.58 10.24C15.58 10.24 15.4 10.42 15.22 10.6C15.22 10.6 15.01 10.74 14.77 10.84C14.77 10.84 14.53 10.95 14.27 11L11 11L11 13L12.5 13C12.64 13 12.75 13.05 12.85 13.15C12.85 13.15 12.95 13.25 13 13.36C13 13.64 12.95 13.75 12.85 13.85C12.85 13.85 12.75 13.95 12.64 14Z"/>
|
||||
<path fill="@image.color2" d="M1.5 16C1.302 16 1.112 15.96 0.9297 15.88C0.9297 15.88 0.7474 15.8 0.5859 15.7C0.5859 15.7 0.4453 15.55 0.3047 15.41C0.3047 15.41 0.1953 15.25 0.1172 15.07C0.1172 15.07 0.0391 14.89 0 14.7L0 7.5C0 7.292 0.0391 7.096 0.1172 6.914C0.1172 6.914 0.1953 6.732 0.3047 6.573C0.3047 6.573 0.4453 6.438 0.5859 6.302C0.5859 6.302 0.7474 6.195 0.9297 6.117C0.9297 6.117 1.112 6.039 1.302 6L4.5 6C4.708 6 4.904 6.039 5.086 6.117C5.086 6.117 5.268 6.195 5.427 6.302C5.427 6.302 5.562 6.438 5.698 6.573C5.698 6.573 5.805 6.732 5.883 6.914C5.883 6.914 5.961 7.096 6 7.292L6 14.5C6 14.7 5.961 14.89 5.883 15.07C5.883 15.07 5.805 15.25 5.698 15.41C5.698 15.41 5.562 15.55 5.427 15.7C5.427 15.7 5.268 15.8 5.086 15.88C5.086 15.88 4.904 15.96 4.708 16ZM4.5 15C4.635 15 4.753 14.95 4.852 14.85C4.852 14.85 4.95 14.75 5 14.64L5 7.5C5 7.365 4.95 7.247 4.852 7.148C4.852 7.148 4.753 7.05 4.635 7L1.5 7C1.365 7 1.247 7.05 1.148 7.148C1.148 7.148 1.05 7.247 1 7.365L1 14.5C1 14.64 1.05 14.75 1.148 14.85C1.148 14.85 1.247 14.95 1.365 15ZM2.5 14C2.365 14 2.247 13.95 2.148 13.85C2.148 13.85 2.05 13.75 2 13.64C2 13.36 2.05 13.25 2.148 13.15C2.148 13.15 2.247 13.05 2.365 13L3.5 13C3.635 13 3.753 13.05 3.852 13.15C3.852 13.15 3.951 13.25 4 13.36C4 13.64 3.951 13.75 3.852 13.85C3.852 13.85 3.753 13.95 3.635 14Z"/>
|
||||
</svg>'
|
||||
|
||||
@disk_management='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M0 9C0 8.427 0.0677 7.87 0.2031 7.328C0.2031 7.328 0.3385 6.787 0.5313 6.271C0.5313 6.271 0.7813 5.781 1.031 5.292C1.031 5.292 1.339 4.836 1.703 4.414C1.703 4.414 2.068 3.992 2.484 3.615C3.422 2.948 3.906 2.685 4.406 2.492C4.406 2.492 4.906 2.3 5.438 2.156C6.021 2.062 6.042 2.062 6.062 2.062C6.062 2.062 6.083 2.062 6.104 2.062C6.26 2.062 6.38 2.089 6.484 2.141C6.484 2.141 6.589 2.193 6.68 2.26C6.68 2.26 6.758 2.344 6.836 2.427C6.836 2.427 6.896 2.526 6.938 2.641C6.938 2.641 6.979 2.755 7 2.875L7 9L13 9C13.12 9 13.24 9.021 13.36 9.062C13.36 9.062 13.47 9.104 13.57 9.164C13.57 9.164 13.66 9.242 13.74 9.32C13.74 9.32 13.81 9.412 13.86 9.516C13.86 9.516 13.91 9.62 13.94 9.74C13.94 9.896 13.94 9.917 13.94 9.938C13.94 9.938 13.94 9.958 13.94 9.979C13.84 10.56 13.7 11.09 13.51 11.59C13.51 11.59 13.32 12.09 13.05 12.58C12.39 13.52 12.01 13.93 11.59 14.3C11.59 14.3 11.16 14.66 10.71 14.97C10.71 14.97 10.22 15.22 9.729 15.47C9.729 15.47 9.213 15.66 8.672 15.8C8.672 15.8 8.13 15.93 7.573 16C6.354 16 5.734 15.92 5.141 15.75C5.141 15.75 4.547 15.58 3.99 15.35C3.99 15.35 3.469 15.04 2.948 14.73C2.948 14.73 2.477 14.37 2.055 13.95C2.055 13.95 1.633 13.52 1.268 13.05C1.268 13.05 0.9609 12.53 0.6537 12.01C0.6537 12.01 0.4167 11.45 0.25 10.86C0.25 10.86 0.0833 10.27 0 9.646ZM12.92 10L7 10C6.865 10 6.734 9.974 6.609 9.922C6.609 9.922 6.484 9.87 6.378 9.8C6.378 9.8 6.289 9.711 6.2 9.622C6.2 9.622 6.13 9.516 6.078 9.391C6.078 9.391 6.026 9.266 6 9.135L6 3.078C5.521 3.162 5.065 3.297 4.633 3.484C4.633 3.484 4.2 3.672 3.8 3.904C3.8 3.904 3.43 4.18 3.06 4.456C3.06 4.456 2.724 4.771 2.422 5.125C2.422 5.125 2.12 5.479 1.865 5.862C1.865 5.862 1.656 6.273 1.448 6.685C1.448 6.685 1.286 7.12 1.172 7.578C1.172 7.578 1.057 8.037 1 8.51C1 9.552 1.073 10.08 1.219 10.59C1.219 10.59 1.365 11.1 1.568 11.58C1.568 11.58 1.828 12.02 2.089 12.47C2.089 12.47 2.401 12.87 2.766 13.23C2.766 13.23 3.13 13.6 3.534 13.91C3.534 13.91 3.977 14.17 4.419 14.43C4.419 14.43 4.896 14.64 5.406 14.78C5.406 14.78 5.917 14.93 6.448 15C7.49 15 7.964 14.94 8.422 14.83C8.422 14.83 8.88 14.71 9.315 14.55C9.315 14.55 9.727 14.34 10.14 14.14C10.14 14.14 10.52 13.88 10.88 13.58C10.88 13.58 11.23 13.28 11.54 12.94C11.54 12.94 11.82 12.57 12.1 12.2C12.1 12.2 12.33 11.8 12.52 11.37C12.52 11.37 12.7 10.93 12.84 10.48Z"/>
|
||||
<path fill="@image.color2" d="M9 8C8.865 8 8.734 7.974 8.609 7.922C8.609 7.922 8.484 7.87 8.378 7.8C8.378 7.8 8.289 7.711 8.2 7.622C8.2 7.622 8.13 7.516 8.078 7.391C8.078 7.391 8.026 7.266 8 7.135L8 0.9375C8 0.625 8.096 0.3906 8.289 0.2344C8.289 0.2344 8.482 0.0781 8.719 0C9.635 0 10.25 0.0807 10.84 0.2422C10.84 0.2422 11.42 0.4036 11.98 0.6328C11.98 0.6328 12.5 0.9297 13.02 1.227C13.02 1.227 13.5 1.591 13.93 2.023C13.93 2.023 14.36 2.456 14.74 2.943C15.4 4.068 15.64 4.654 15.78 5.242C15.78 5.242 15.93 5.831 16 6.458C16 7.25 15.97 7.367 15.92 7.477C15.92 7.477 15.87 7.586 15.8 7.68C15.8 7.68 15.72 7.758 15.64 7.836C15.64 7.836 15.54 7.896 15.42 7.938C15.42 7.938 15.31 7.979 15.19 8ZM15 7C15 6.167 14.84 5.388 14.53 4.664C14.53 4.664 14.22 3.94 13.79 3.305C13.79 3.305 13.24 2.758 12.7 2.211C12.7 2.211 12.06 1.781 11.34 1.469C11.34 1.469 10.61 1.156 9.833 1L9 7Z"/>
|
||||
</svg>'
|
||||
|
||||
@filter='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M0 2.5C0 2.292 0.0391 2.096 0.1172 1.914C0.1172 1.914 0.1953 1.732 0.3021 1.573C0.3021 1.573 0.4375 1.438 0.5729 1.302C0.5729 1.302 0.7318 1.195 0.9141 1.117C0.9141 1.117 1.096 1.039 1.292 1L14.5 1C14.71 1 14.9 1.039 15.09 1.117C15.09 1.117 15.27 1.195 15.43 1.302C15.43 1.302 15.56 1.438 15.7 1.573C15.7 1.573 15.8 1.732 15.88 1.914C15.88 1.914 15.96 2.096 16 2.292C16 2.927 15.84 3.287 15.53 3.578L10.47 8.406C10.4 8.479 10.33 8.557 10.27 8.641C10.27 8.641 10.22 8.724 10.17 8.812C10.04 9.083 10 9.281 10 9.5L10 15.5C10 15.64 9.95 15.75 9.852 15.85C9.852 15.85 9.753 15.95 9.635 16C9.406 16 9.318 15.97 9.234 15.91L6.234 13.91C6.078 13.81 6 13.68 6 13.5L6 9.5C6 9.292 5.964 9.094 5.891 8.906C5.849 8.812 5.797 8.724 5.734 8.641C5.734 8.641 5.672 8.557 5.604 8.479L0.4688 3.578C0.1563 3.287 0 2.927 0 2.5ZM15 2.484C15 2.349 14.95 2.234 14.85 2.141C14.85 2.141 14.75 2.047 14.64 2L1.5 2C1.365 2 1.247 2.047 1.148 2.141C1.148 2.141 1.05 2.234 1 2.349C1 2.641 1.052 2.766 1.156 2.859L6.234 7.688C6.474 7.917 6.662 8.19 6.797 8.508C6.797 8.508 6.932 8.825 7 9.156L7 13.23L9 14.56L9 9.5C9 9.156 9.068 8.825 9.203 8.508C9.203 8.508 9.338 8.19 9.531 7.917L14.84 2.859C14.95 2.766 15 2.641 15 2.484Z"/>
|
||||
</svg>'
|
||||
|
||||
@window ='<svg fill="none" viewBox="0 0 16 16">
|
||||
@svg_window_template
|
||||
</svg>'
|
||||
|
||||
@code='<svg fill="none">
|
||||
<path fill="@image.color1" d="M70.6,25.4c0.6-0.6,0.5-1.7,0-2.3L67.5,20L53.7,6.6c-0.6-0.6-1.5-0.6-2.2,0l0,0c-0.6,0.6-0.8,1.7,0,2.3 L66,23.1c0.6,0.6,0.6,1.7,0,2.3L51.2,40.1c-0.6,0.6-0.6,1.7,0,2.3l0,0c0.6,0.6,1.7,0.5,2.2,0l13.7-13.6c0,0,0,0,0.1-0.1L70.6,25.4z"/>
|
||||
<path fill="@image.color1" d="M7.4,25.4c-0.6-0.6-0.5-1.7,0-2.3l3.1-3.1L24.3,6.6c0.6-0.6,1.5-0.6,2.2,0l0,0c0.6,0.6,0.8,1.7,0,2.3 L12.3,23.1c-0.6,0.6-0.6,1.7,0,2.3l14.5,14.7c0.6,0.6,0.6,1.7,0,2.3l0,0c-0.6,0.6-1.7,0.5-2.2,0L10.6,29c0,0,0,0-0.1-0.1L7.4,25.4z"/>
|
||||
<polygon fill="#FCD116" points="54.6,-4.5 35.1,-4.5 24.6,25.1 37.4,25.2 27.4,54.5 55,15.4 41.6,15.4 "/>
|
||||
</svg>'
|
||||
|
||||
@reddit='<svg fill="none" viewBox="0 0 16 16">
|
||||
<path fill="@image.color1" d="M13.7 6.4C14.2 6.4 14.6 6.6 15 7C15.2 7.3 15.3 7.7 15.3 8C15.3 8.2 15.3 8.2 15.3 8.3C15.2 8.9 14.9 9.2 14.4 9.4C14.5 9.7 14.5 9.9 14.5 10.2C14.5 11.1 14.2 11.9 13.6 12.6C13 13.3 12.2 13.9 11.3 14.3C10.2 14.7 9.2 15 8 15C6.8 15 5.7 14.7 4.8 14.3C3.8 13.9 3 13.3 2.3 12.6C1.8 11.9 1.4 11.1 1.4 10.2C1.4 10 1.5 9.8 1.5 9.5C1 9.2 .7 8.9 .6 8.3C.6 8.2 .6 8.2 .6 8C.6 7.7 .7 7.3 1 7C1.3 6.6 1.7 6.4 2.2 6.4C2.2 6.4 2.2 6.4 2.2 6.4C2.7 6.4 3.1 6.6 3.4 6.9C4.6 6.1 6 5.6 7.7 5.6C7.7 5.6 8 4.2 8.6 1.3C8.6 1.2 8.6 1.2 8.7 1.1C94.4 1.1 8.8 1 8.9 1C8.9 1 9 1 9 1C9 1 9.9 1.3 11.9 1.8C12.1 1.5 12.2 1.4 12.4 1.3C12.6 1.1 12.8 1 13 1C13.4 1 13.7 1.2 13.9 1.4C14.2 1.7 14.2 1.9 14.2 2.3C14.2 2.6 14.2 3 13.9 3.2C13.7 3.4 13.4 3.5 13 3.5C12.7 3.5 12.4 3.4 12.2 3.2C11.9 3 11.8 2.6 11.8 2.3C11.8 2.3 11 2.1 9.1 1.7L8.2 5.6C9 5.6 9.8 5.7 10.6 5.9C11.3 6.2 11.9 6.5 12.5 6.9C12.8 6.6 13.2 6.4 13.7 6.4Z"/>
|
||||
</svg>'
|
||||
|
||||
@cortana,show_cortana_button='<svg fill="none" viewBox="0 0 16 16">
|
||||
<circle cx="8" cy="8" r="7" stroke="@image.color1" />
|
||||
<circle cx="8" cy="8" r="5.5" stroke="@image.color2" />
|
||||
</svg>'
|
||||
|
||||
@nvidia='<svg fill="none" viewBox="0 0 24 24">
|
||||
<path fill="@image.color1" d="M8.948 8.798v-1.43a6.7 6.7 0 0 1 .424-.018c3.922-.124 6.493 3.374 6.493 3.374s-2.774 3.851-5.75 3.851c-.398 0-.787-.062-1.158-.185v-4.346c1.528.185 1.837.857 2.747 2.385l2.04-1.714s-1.492-1.952-4-1.952a6.016 6.016 0 0 0-.796.035m0-4.735v2.138l.424-.027c5.45-.185 9.01 4.47 9.01 4.47s-4.08 4.964-8.33 4.964c-.37 0-.733-.035-1.095-.097v1.325c.3.035.61.062.91.062 3.957 0 6.82-2.023 9.593-4.408.459.371 2.34 1.263 2.73 1.652-2.633 2.208-8.772 3.984-12.253 3.984-.335 0-.653-.018-.971-.053v1.864H24V4.063z"/>
|
||||
<path fill="@image.color2" d="m0 10.326v1.131c-3.657-.654-4.673-4.46-4.673-4.46s1.758-1.944 4.673-2.262v1.237H8.94c-1.528-.186-2.73 1.245-2.73 1.245s.68 2.412 2.739 3.11M2.456 10.9s2.164-3.197 6.5-3.533V6.201C4.153 6.59 0 10.653 0 10.653s2.35 6.802 8.948 7.42v-1.237c-4.84-.6-6.492-5.936-6.492-5.936z"/>
|
||||
</svg>'
|
||||
@@ -0,0 +1,44 @@
|
||||
/*
|
||||
Arabic
|
||||
by: github.com/moudey
|
||||
*/
|
||||
|
||||
// shell.nss
|
||||
pin_unpin="Pin/Unpin"
|
||||
|
||||
// develop.nss
|
||||
develop="تطوير"
|
||||
editors="محررات"
|
||||
windows_notepad="مفكرة الويندوز"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="ادارة الملفات"
|
||||
change_extension="تغير الملحقات"
|
||||
take_ownership="Take ownership"
|
||||
show_hide="اظهار/اخفاء"
|
||||
system_files="ملفات النظام"
|
||||
file_name_extensions="File name extensions"
|
||||
attributes="السمات"
|
||||
register_server="Register Server"
|
||||
register="تسجيل"
|
||||
unregister="الغاء التسجيل"
|
||||
hidden="اخفاء"
|
||||
system="النظام"
|
||||
readonly="قراءة فقط"
|
||||
archive="ارشيف"
|
||||
created="Created"
|
||||
modified="Modified"
|
||||
accessed="Accessed"
|
||||
new_folder="مجلد جديد"
|
||||
new_file="ملف جديد"
|
||||
datetime="تاريخ ووقت"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
all_control_panel_items="جميع عناصر لوحة التحكم"
|
||||
|
||||
// taskbar.nss
|
||||
apps="تطبيقات"
|
||||
paint="الرسام"
|
||||
edge="Edge"
|
||||
calculator="الحاسبة"
|
||||
@@ -0,0 +1,82 @@
|
||||
/*
|
||||
German
|
||||
by: github.com/akaydev-coder
|
||||
*/
|
||||
|
||||
xxx="Begrüßung auf Deutsch"
|
||||
// shell.nss
|
||||
pin_unpin="Anpinnen/Lösen"
|
||||
|
||||
// develop.nss
|
||||
develop="&Entwickeln"
|
||||
editors="Herausgeber"
|
||||
windows_notepad="Windows-Notpad"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="Dateiverwaltung"
|
||||
all="Alle"
|
||||
invert="Umkehren"
|
||||
none="Keiner"
|
||||
change_extension="Erweiterung ändern"
|
||||
take_ownership="Eigentümer ändern"
|
||||
show_hide="Ein-/Ausblenden"
|
||||
system_files="Systemdateien"
|
||||
file_name_extensions="Dateinamenerweiterungen"
|
||||
attributes="Attribute"
|
||||
register_server="DLL-Server Registrieren"
|
||||
register="Registrieren"
|
||||
unregister="de-Registrieren"
|
||||
hidden="Versteckt"
|
||||
system="System"
|
||||
readonly="Schreibgeschützt"
|
||||
archive="Archiv"
|
||||
created="Erstellt"
|
||||
modified="Geändert"
|
||||
accessed="Zugegriffen"
|
||||
new_folder="Neuer Ordner"
|
||||
new_file="Neue Datei"
|
||||
datetime="Datum/Uhrzeit"
|
||||
guid="GUID"
|
||||
|
||||
// goto.nss
|
||||
folder="Ordner"
|
||||
all_control_panel_items="Alle Elemente der Systemsteuerung"
|
||||
system="System"
|
||||
about="Über"
|
||||
your_info="Ihre Infos"
|
||||
system_info="Systeminformationen"
|
||||
search="Suchen"
|
||||
usb="USB"
|
||||
windows_update="Windows-Update"
|
||||
windows_defender="Windows Defender"
|
||||
apps="Apps"
|
||||
apps_features="Apps-Features"
|
||||
default_apps="Standard-Apps"
|
||||
optional_features="Optionale Features"
|
||||
startup="Start-up"
|
||||
personalization="Personalisierung"
|
||||
lockscreen="Sperrbildschirm"
|
||||
background="Hintergrund"
|
||||
colors="Farben"
|
||||
themes="Themen"
|
||||
start="Start"
|
||||
taskbar="Taskleiste"
|
||||
network="Netzwerk"
|
||||
status="Status"
|
||||
ethernet="Ethernet"
|
||||
wifi="WLAN"
|
||||
connections="Verbindungen"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="Apps"
|
||||
paint="Paint"
|
||||
edge="Edge"
|
||||
calculator="Taschenrechner"
|
||||
cascade_windows="Fenster Kaskadenieren"
|
||||
Show_windows_stacked="Fenster gestapelt anzeigen"
|
||||
Show_windows_side_by_side="Fenster nebeneinander anzeigen"
|
||||
minimize_all_windows="Minimieren Sie alle Fenster"
|
||||
restore_all_windows="Alle Fenster wiederherstellen"
|
||||
task_manager="Task-Manager"
|
||||
taskbar_Settings="Taskleisteneinstellungen"
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
English
|
||||
by: github.com/moudey
|
||||
*/
|
||||
|
||||
xxx="Welcome in english"
|
||||
// shell.nss
|
||||
pin_unpin="Pin/Unpin"
|
||||
|
||||
// develop.nss
|
||||
develop="&Develop"
|
||||
editors="editors"
|
||||
windows_notepad="Windows notepad"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="File manage"
|
||||
copy_multiple_paths='Copy (@sel.count) items selected'
|
||||
all="All"
|
||||
invert="Invert"
|
||||
none="None"
|
||||
change_extension="Change extension"
|
||||
take_ownership="Take ownership"
|
||||
show_hide="Show/Hide"
|
||||
system_files="System files"
|
||||
file_name_extensions="File name extensions"
|
||||
attributes="Attributes"
|
||||
register_server="Register Server"
|
||||
register="Register"
|
||||
unregister="Unregister"
|
||||
hidden="Hidden"
|
||||
system="System"
|
||||
readonly="Read-Only"
|
||||
archive="Archive"
|
||||
created="Created"
|
||||
modified="Modified"
|
||||
accessed="Accessed"
|
||||
new_folder="New Folder"
|
||||
new_file="New File"
|
||||
datetime="DateTime"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
folder="Folder"
|
||||
all_control_panel_items="All Control Panel Items"
|
||||
system="System"
|
||||
about="About"
|
||||
your_info="Your Info"
|
||||
system_info="System Info"
|
||||
search="Search"
|
||||
usb="USB"
|
||||
windows_update="Windows Update"
|
||||
windows_defender="Windows Defender"
|
||||
apps="Apps"
|
||||
apps_features="Apps Features"
|
||||
default_apps="Default Apps"
|
||||
optional_features="Optional Features"
|
||||
startup="Startup"
|
||||
personalization="Personalization"
|
||||
lockscreen="Lockscreen"
|
||||
background="Background"
|
||||
colors="Colors"
|
||||
themes="Themes"
|
||||
start="Start"
|
||||
taskbar="Taskbar"
|
||||
network="Network"
|
||||
status="Status"
|
||||
ethernet="Ethernet"
|
||||
wifi="WLAN"
|
||||
connections="Connections"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="Apps"
|
||||
paint="Paint"
|
||||
edge="Edge"
|
||||
calculator="Calculator"
|
||||
windows="windows"
|
||||
cascade_windows="Cascade windows"
|
||||
Show_windows_stacked="Show windows stacked"
|
||||
Show_windows_side_by_side="Show windows side by side"
|
||||
minimize_all_windows="Minimize all windows"
|
||||
restore_all_windows="Restore all windows"
|
||||
task_manager="Task Manager"
|
||||
taskbar_Settings="Taskbar Settings"
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
Spanish
|
||||
by: github.com/kevindeoz
|
||||
*/
|
||||
|
||||
xxx="Bienvenido"
|
||||
// shell.nss
|
||||
pin_unpin="Anclar/Desanclar"
|
||||
|
||||
// develop.nss
|
||||
develop="&Desarrollo"
|
||||
editors="Editores"
|
||||
windows_notepad="Bloc de Notas"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="Gestión de Archivos"
|
||||
copy_multiple_paths='Copiar (@sel.count) elementos seleccionados'
|
||||
all="Todos"
|
||||
invert="Inverso"
|
||||
none="Nada"
|
||||
change_extension="Cambiar extensión"
|
||||
take_ownership="Tomar Posesión"
|
||||
show_hide="Mostrar/Ocultar"
|
||||
system_files="Archivos del Sistema"
|
||||
file_name_extensions="Extensiones de nombre de archivo"
|
||||
attributes="Atributos"
|
||||
register_server="Registrar Servicio"
|
||||
register="Registrar"
|
||||
unregister="Cancelar registro"
|
||||
hidden="Oculto"
|
||||
system="Sistema"
|
||||
readonly="Sólo Lectura"
|
||||
archive="Archivo"
|
||||
created="Creado"
|
||||
modified="Modificado"
|
||||
accessed="Acceso"
|
||||
new_folder="Nueva Carpeta"
|
||||
new_file="Nuevo Archivo"
|
||||
datetime="Fecha/Hora"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
folder="Carpeta"
|
||||
all_control_panel_items="Todos los elementos del Panel de Control"
|
||||
system="Sistema"
|
||||
about="Acerca de"
|
||||
your_info="Tu Información"
|
||||
system_info="Información del Sistema"
|
||||
search="Búsqueda"
|
||||
usb="USB"
|
||||
windows_update="Windows Update"
|
||||
windows_defender="Windows Defender"
|
||||
apps="Aplicaciones"
|
||||
apps_features="Aplicaciones instaladas"
|
||||
default_apps="Aplicaciones predeterminadas"
|
||||
optional_features="Características opcionales"
|
||||
startup="Inicialización"
|
||||
personalization="Personalización"
|
||||
lockscreen="Pantalla de bloqueo"
|
||||
background="Fondo"
|
||||
colors="Colores"
|
||||
themes="Temas"
|
||||
start="Inicio"
|
||||
taskbar="Barra de tareas"
|
||||
network="Red e Internet"
|
||||
status="Estado"
|
||||
ethernet="Ethernet"
|
||||
wifi="Wi-Fi"
|
||||
connections="Conexiones de red"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="Aplicaciones"
|
||||
paint="Paint"
|
||||
edge="Edge"
|
||||
calculator="Calculadora"
|
||||
windows="Ventanas"
|
||||
cascade_windows="Ventanas en cascada"
|
||||
Show_windows_stacked="Ventanas apiladas"
|
||||
Show_windows_side_by_side="Ventanas lado a lado"
|
||||
minimize_all_windows="Minimizar todas las ventanas"
|
||||
restore_all_windows="Restaurar todas las ventanas"
|
||||
task_manager="Administrador de tareas"
|
||||
taskbar_Settings="Configuración de barra de tareas"
|
||||
@@ -0,0 +1,83 @@
|
||||
/*
|
||||
Italian
|
||||
by: Andrea Brandi <andreabrandi.com>
|
||||
*/
|
||||
|
||||
xxx="Benvenuti in italiano"
|
||||
// shell.nss
|
||||
pin_unpin="Blocca/Sblocca"
|
||||
|
||||
// develop.nss
|
||||
develop="&Sviluppo"
|
||||
editors="Editor"
|
||||
windows_notepad="Blocco note"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="Gestione file"
|
||||
copy_multiple_paths='Copia (@sel.count) elementi selezionati'
|
||||
all="Tutti"
|
||||
invert="Inverti"
|
||||
none="Nessuno"
|
||||
change_extension="Cambia estensione"
|
||||
take_ownership="Diventa proprietario"
|
||||
show_hide="Mostra/Nascondi"
|
||||
system_files="File di sistema"
|
||||
file_name_extensions="Estensioni nomi file"
|
||||
attributes="Attributi"
|
||||
register_server="Register server"
|
||||
register="Registra"
|
||||
unregister="Rimuovi"
|
||||
hidden="Nascosto"
|
||||
system="Sistema"
|
||||
readonly="Sola lettura"
|
||||
archive="Archivio"
|
||||
created="Creato"
|
||||
modified="Modificato"
|
||||
accessed="Ultimo accesso"
|
||||
new_folder="Nuova cartella"
|
||||
new_file="Nuovo file"
|
||||
datetime="Data/ora"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
folder="Cartella"
|
||||
all_control_panel_items="Tutte le attività"
|
||||
system="Sistema"
|
||||
about="Informazioni"
|
||||
your_info="Le tue info"
|
||||
system_info="Informazioni di sistema"
|
||||
search="Cerca"
|
||||
usb="USB"
|
||||
windows_update="Windows Update"
|
||||
windows_defender="Windows Defender"
|
||||
apps="App"
|
||||
apps_features="App e funzionalità"
|
||||
default_apps="App predefinite"
|
||||
optional_features="Funzionalità facoltative"
|
||||
startup="Avvio"
|
||||
personalization="Personalizzazione"
|
||||
lockscreen="Schermata di blocco"
|
||||
background="Sfondo"
|
||||
colors="Colori"
|
||||
themes="Temi"
|
||||
start="Start"
|
||||
taskbar="Barra delle applicazioni"
|
||||
network="Rete"
|
||||
status="Stato"
|
||||
ethernet="Ethernet"
|
||||
wifi="Wi-Fi"
|
||||
connections="Connessioni"
|
||||
|
||||
// taskbar.nss
|
||||
apps="App"
|
||||
paint="Paint"
|
||||
edge="Edge"
|
||||
calculator="Calcolatrice"
|
||||
windows="Finestre"
|
||||
cascade_windows="Finestre a cascata"
|
||||
Show_windows_stacked="Finestre sovrapposte"
|
||||
Show_windows_side_by_side="Finestre affiancate"
|
||||
minimize_all_windows="Minimizza tutte le finestre"
|
||||
restore_all_windows="Ripristina tutte le finestre"
|
||||
task_manager="Gestione attività"
|
||||
taskbar_Settings="Impostazioni barra"
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
Japanese
|
||||
by: github.com/maboroshin
|
||||
*/
|
||||
|
||||
xxx="ようこそ"
|
||||
// shell.nss
|
||||
pin_unpin="ピン留め/外す"
|
||||
|
||||
// develop.nss
|
||||
develop="開発(&D)"
|
||||
editors="エディター"
|
||||
windows_notepad="Windows メモ帳"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="ファイル管理"
|
||||
copy_multiple_paths='選択済みの (@sel.count) 項目をコピー'
|
||||
all="すべて"
|
||||
invert="反転"
|
||||
none="なし"
|
||||
change_extension="拡張子を変更"
|
||||
take_ownership="所有権の取得"
|
||||
show_hide="表示/非表示"
|
||||
system_files="システムファイル"
|
||||
file_name_extensions="ファイルの拡張子"
|
||||
attributes="属性"
|
||||
register_server="サーバー登録"
|
||||
register="登録"
|
||||
unregister="登録解除"
|
||||
hidden="隠し"
|
||||
system="システム"
|
||||
readonly="読み取り専用"
|
||||
archive="アーカイブ"
|
||||
created="作成日時"
|
||||
modified="更新日時"
|
||||
accessed="アクセス日時"
|
||||
new_folder="新しいフォルダ"
|
||||
new_file="新しいファイル"
|
||||
datetime="日時"
|
||||
guid="GUID"
|
||||
|
||||
// goto.nss
|
||||
folder="フォルダー"
|
||||
all_control_panel_items="コントロールパネル全項目"
|
||||
system="システム"
|
||||
about="情報"
|
||||
your_info="ユーザーの情報"
|
||||
system_info="システムの情報"
|
||||
search="検索"
|
||||
usb="USB"
|
||||
windows_update="Windows Update"
|
||||
windows_defender="Windows セキュリティ"
|
||||
apps="アプリ"
|
||||
apps_features="アプリと機能"
|
||||
default_apps="既定のアプリ"
|
||||
optional_features="オプション機能"
|
||||
startup="スタートアップ"
|
||||
personalization="個人用設定"
|
||||
lockscreen="ロック画面"
|
||||
background="背景"
|
||||
colors="色"
|
||||
themes="テーマ"
|
||||
start="スタート"
|
||||
taskbar="タスクバー"
|
||||
network="ネットワーク"
|
||||
status="状態"
|
||||
ethernet="イーサネット"
|
||||
wifi="WiFi"
|
||||
connections="ネットワーク接続"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="アプリ"
|
||||
paint="ペイント"
|
||||
edge="Edge"
|
||||
calculator="電卓"
|
||||
windows="ウィンドウ"
|
||||
cascade_windows="重ねて表示"
|
||||
Show_windows_stacked="ウィンドウを上下に並べて表示"
|
||||
Show_windows_side_by_side="ウィンドウを左右に並べて表示"
|
||||
minimize_all_windows="すべてのウィンドウを最小化"
|
||||
restore_all_windows="すべてのウィンドウを復元"
|
||||
task_manager="タスクマネージャー"
|
||||
taskbar_Settings="タスクバーの設定"
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
Korean
|
||||
by: github.com/venusgirl
|
||||
*/
|
||||
|
||||
xxx="한국어 번역 - 비너스걸"
|
||||
// shell.nss
|
||||
pin_unpin="고정/고정 해제"
|
||||
|
||||
// develop.nss
|
||||
develop="개발(&D)"
|
||||
editors="편집기"
|
||||
windows_notepad="Windows 메모장"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="파일 관리"
|
||||
copy_multiple_paths='선택한 항목 복사 (@sel.count)'
|
||||
all="모두"
|
||||
invert="반전"
|
||||
none="없음"
|
||||
change_extension="확장자 변경"
|
||||
take_ownership="소유권 확보"
|
||||
show_hide="표시/숨기기"
|
||||
system_files="시스템 파일"
|
||||
file_name_extensions="파일 이름 확장자"
|
||||
attributes="속성"
|
||||
register_server="서버 등록"
|
||||
register="등록"
|
||||
unregister="등록 해제"
|
||||
hidden="숨기기"
|
||||
system="시스템"
|
||||
readonly="읽기 전용"
|
||||
archive="보관"
|
||||
created="만든 날짜"
|
||||
modified="수정 날짜"
|
||||
accessed="접근 날짜"
|
||||
new_folder="새 폴더"
|
||||
new_file="새 파일"
|
||||
datetime="날짜 시간"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
folder="폴더"
|
||||
all_control_panel_items="모든 제어판 항목"
|
||||
system="시스템"
|
||||
about="정보"
|
||||
your_info="사용자 정보"
|
||||
system_info="시스템 정보"
|
||||
search="검색"
|
||||
usb="USB"
|
||||
windows_update="Windows 업데이트"
|
||||
windows_defender="Windows Defender"
|
||||
apps="앱"
|
||||
apps_features="앱 기능"
|
||||
default_apps="기본 앱"
|
||||
optional_features="선택적 기능"
|
||||
startup="시작"
|
||||
personalization="개인 설정"
|
||||
lockscreen="화면 잠금"
|
||||
background="배경"
|
||||
colors="색상"
|
||||
themes="테마"
|
||||
start="시작"
|
||||
taskbar="작업 표시줄"
|
||||
network="네트워크"
|
||||
status="상태"
|
||||
ethernet="이더넷"
|
||||
wifi="WLAN"
|
||||
connections="연결"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="앱"
|
||||
paint="그림판"
|
||||
edge="Edge"
|
||||
calculator="계산기"
|
||||
windows="창"
|
||||
cascade_windows="계단식 창"
|
||||
Show_windows_stacked="겹쳐진 창 표시"
|
||||
Show_windows_side_by_side="창을 나란히 표시"
|
||||
minimize_all_windows="모든 창 최소화"
|
||||
restore_all_windows="모든 창 복원"
|
||||
task_manager="작업 관리자"
|
||||
taskbar_Settings="작업 관리자 설정"
|
||||
@@ -0,0 +1,82 @@
|
||||
/*
|
||||
Norwegian
|
||||
by: https://github.com/Vatnar
|
||||
*/
|
||||
|
||||
xxx="Velkommen på norsk"
|
||||
// shell.nss
|
||||
pin_unpin="Fest/Løsne"
|
||||
|
||||
// develop.nss
|
||||
develop="&Utvikle"
|
||||
editors="editorer"
|
||||
windows_notepad="Windows notepad"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="Administrer fil"
|
||||
all="Alle"
|
||||
invert="Inverter"
|
||||
none="Ingen"
|
||||
change_extension="Endre filtype"
|
||||
take_ownership="Ta eierskap"
|
||||
show_hide="Vis/Skjul"
|
||||
system_files="Systemfiler"
|
||||
file_name_extensions="Filtypenavn"
|
||||
attributes="Attributter"
|
||||
register_server="Registrer Server"
|
||||
register="Registrer"
|
||||
unregister="Avregistrer"
|
||||
hidden="Skjult"
|
||||
system="System"
|
||||
readonly="Skrivebeskyttet"
|
||||
archive="Arkiv"
|
||||
created="Skapt"
|
||||
modified="Endret"
|
||||
accessed="Aksessert"
|
||||
new_folder="Ny Mappe"
|
||||
new_file="Ny Fil"
|
||||
datetime="tidsdato"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
folder="Mappe"
|
||||
all_control_panel_items="Alle kontrollpanelelementer"
|
||||
system="System"
|
||||
about="Om"
|
||||
your_info="Infoen din"
|
||||
system_info="Systeminfo"
|
||||
search="Søk"
|
||||
usb="USB"
|
||||
windows_update="Windows Update"
|
||||
windows_defender="Windows Defender"
|
||||
apps="Apper"
|
||||
apps_features="Apper og funksjoner"
|
||||
default_apps="Standardapper"
|
||||
optional_features="Valgfrie funksjoner"
|
||||
startup="Oppstart"
|
||||
personalization="Personalisering"
|
||||
lockscreen="Låseskjerm"
|
||||
background="Bakgrunn"
|
||||
colors="Farger"
|
||||
themes="Temaer"
|
||||
start="Start"
|
||||
taskbar="Oppgavelinje"
|
||||
network="Nettverk"
|
||||
status="Status"
|
||||
ethernet="Ethernet"
|
||||
wifi="WLAN"
|
||||
connections="Tilkoblinger"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="Apper"
|
||||
paint="Paint"
|
||||
edge="Edge"
|
||||
calculator="Kalkulator"
|
||||
cascade_windows="Kaskadér vinduer"
|
||||
Show_windows_stacked="Vis vinduer stablet"
|
||||
Show_windows_side_by_side="Vis vinduer side om side"
|
||||
minimize_all_windows="Minimer alle vinduer"
|
||||
restore_all_windows="Gjenopprett alle vinduer"
|
||||
task_manager="Oppgavebehandling"
|
||||
taskbar_Settings="Alternativer for oppgavelinjen"
|
||||
@@ -0,0 +1,82 @@
|
||||
/*
|
||||
Português do Brasil
|
||||
by: github.com/marciozomb13
|
||||
*/
|
||||
|
||||
xxx="Bem-vindo"
|
||||
// shell.nss
|
||||
pin_unpin="Fixar/Desafixar"
|
||||
|
||||
// develop.nss
|
||||
develop="&Desenvolvimento"
|
||||
editors="Editores"
|
||||
windows_notepad="Bloco de Notas"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="Gerenciamento de arquivos"
|
||||
all="Todos"
|
||||
invert="Inverter"
|
||||
none="Nenhum"
|
||||
change_extension="Alterar extensão"
|
||||
take_ownership="Obter propriedade"
|
||||
show_hide="Mostrar/Ocultar"
|
||||
system_files="Arquivos de sistema"
|
||||
file_name_extensions="Extensões de arquivos"
|
||||
attributes="Atributos"
|
||||
register_server="Servidor de Registro"
|
||||
register="Registrar"
|
||||
unregister="Remover registro"
|
||||
hidden="Oculto"
|
||||
system="Sistema"
|
||||
readonly="Somente leitura"
|
||||
archive="Arquivo compactado"
|
||||
created="Criado"
|
||||
modified="Modificado"
|
||||
accessed="Acessado"
|
||||
new_folder="Nova Pasta"
|
||||
new_file="Novo Arquivo"
|
||||
datetime="Data/Hora"
|
||||
guid="GUID"
|
||||
|
||||
// goto.nss
|
||||
folder="Pasta"
|
||||
all_control_panel_items="Todos os Itens do Painel de Controle"
|
||||
system="Sistema"
|
||||
about="Sobre"
|
||||
your_info="Suas informações"
|
||||
system_info="Informações do sistema"
|
||||
search="Pesquisa"
|
||||
usb="USB"
|
||||
windows_update="Windows Update"
|
||||
windows_defender="Segurança do Windows"
|
||||
apps="Aplicativos"
|
||||
apps_features="Aplicativos instalados"
|
||||
default_apps="Aplicativos padrão"
|
||||
optional_features="Recursos opcionais"
|
||||
startup="Inicialização"
|
||||
personalization="Personalização"
|
||||
lockscreen="Tela de bloqueio"
|
||||
background="Tela de fundo"
|
||||
colors="Cores"
|
||||
themes="Temas"
|
||||
start="Iniciar"
|
||||
taskbar="Barra de Tarefas"
|
||||
network="Rede e internet"
|
||||
status="Status"
|
||||
ethernet="Ethernet"
|
||||
wifi="WLAN"
|
||||
connections="Conexões de rede"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="Apps"
|
||||
paint="Paint"
|
||||
edge="Edge"
|
||||
calculator="Calculadora"
|
||||
cascade_windows="Janelas em cascata"
|
||||
Show_windows_stacked="Mostrar janelas em empilhadas"
|
||||
Show_windows_side_by_side="Mostrar janelas lado a lado"
|
||||
minimize_all_windows="Minimizar todas as janelas"
|
||||
restore_all_windows="Restaurar todas as janelas"
|
||||
task_manager="Gerenciador de Tarefas"
|
||||
taskbar_Settings="Configurações da Barra de Tarefas"
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
Romanian
|
||||
by: github.com/Valer100
|
||||
*/
|
||||
|
||||
xxx="Bun venit!"
|
||||
// shell.nss
|
||||
pin_unpin="Fixează/Anulează fixarea"
|
||||
|
||||
// develop.nss
|
||||
develop="&Dezvoltare"
|
||||
editors="Aplicații de editare"
|
||||
windows_notepad="Windows Notepad"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="Gestionare fișiere"
|
||||
copy_multiple_paths='Copiază (@sel.count) (de) elemente selectate'
|
||||
all="Toate"
|
||||
invert="Inversează"
|
||||
none="Nimic"
|
||||
change_extension="Modifică extensia"
|
||||
take_ownership="Preia proprietatea"
|
||||
show_hide="Arată/ascunde"
|
||||
system_files="Fișiere de sistem"
|
||||
file_name_extensions="Extensiile fișierelor"
|
||||
attributes="Atribute"
|
||||
register_server="Register Server"
|
||||
register="Înregistrează"
|
||||
unregister="Anulează înregistrarea"
|
||||
hidden="Ascuns"
|
||||
system="Sistem"
|
||||
readonly="Doar în citire"
|
||||
archive="Arhivă"
|
||||
created="Creat"
|
||||
modified="Modificat"
|
||||
accessed="Accesat"
|
||||
new_folder="Folder nou"
|
||||
new_file="Fișier nou"
|
||||
datetime="DateTime"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
folder="Folder"
|
||||
all_control_panel_items="Toate elementele din Panoul de control"
|
||||
system="Sistem"
|
||||
about="Despre"
|
||||
your_info="Informațiile tale"
|
||||
system_info="Informații despre sistem"
|
||||
search="Caută"
|
||||
usb="USB"
|
||||
windows_update="Windows Update"
|
||||
windows_defender="Windows Defender"
|
||||
apps="Aplicații"
|
||||
apps_features="Aplicații și caracteristici"
|
||||
default_apps="Aplicații implicite"
|
||||
optional_features="Caracteristici opționale"
|
||||
startup="Pornire"
|
||||
personalization="Personalizare"
|
||||
lockscreen="Ecran de blocare"
|
||||
background="Fundal"
|
||||
colors="Culori"
|
||||
themes="Teme"
|
||||
start="Start"
|
||||
taskbar="Bară de activități"
|
||||
network="Rețea"
|
||||
status="Status"
|
||||
ethernet="Ethernet"
|
||||
wifi="WLAN"
|
||||
connections="Conexiuni"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="Aplicații"
|
||||
paint="Paint"
|
||||
edge="Edge"
|
||||
calculator="Calculator"
|
||||
windows="Ferestre"
|
||||
cascade_windows="Ferestre în cascadă"
|
||||
Show_windows_stacked="Afișează ferestrele în stivă"
|
||||
Show_windows_side_by_side="Afișează ferestrele una lângă alta"
|
||||
minimize_all_windows="Minimizează toate ferestrele"
|
||||
restore_all_windows="Restaurează toate ferestrele"
|
||||
task_manager="Manager de activități"
|
||||
taskbar_Settings="Setări bară de activități"
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
Russian
|
||||
by: github.com/younyokel
|
||||
*/
|
||||
|
||||
xxx="Добро пожаловать"
|
||||
// shell.nss
|
||||
pin_unpin="Закрепить/Открепить"
|
||||
|
||||
// develop.nss
|
||||
develop="&Разработка"
|
||||
editors="Редакторы"
|
||||
windows_notepad="Блокнот"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="Менеджер файлов"
|
||||
copy_multiple_paths='Скопировать пути выбранных элементов (@sel.count)'
|
||||
all="Все"
|
||||
invert="Инвертировать выделение"
|
||||
none="Ничего"
|
||||
change_extension="Изменить расширение"
|
||||
take_ownership="Стать владельцем"
|
||||
show_hide="Показать/Скрыть"
|
||||
system_files="Скрытые элементы"
|
||||
file_name_extensions="Расширения имен файлов"
|
||||
attributes="Атрибуты"
|
||||
register_server="Зарегистрировать сервер"
|
||||
register="Зарегистрировать"
|
||||
unregister="Удалить регистрацию"
|
||||
hidden="Скрытый"
|
||||
system="Системный"
|
||||
readonly="Только для чтения"
|
||||
archive="Архив"
|
||||
created="Создано"
|
||||
modified="Изменено"
|
||||
accessed="Получен доступ"
|
||||
new_folder="Новая папка"
|
||||
new_file="Новый файл"
|
||||
datetime="Имя: Дата и время"
|
||||
guid="Имя: Идентификатор GUID"
|
||||
|
||||
// goto.nss
|
||||
folder="Папки"
|
||||
all_control_panel_items="Все задачи"
|
||||
system="Главное"
|
||||
about="О системе"
|
||||
your_info="Ваши данные"
|
||||
system_info="Сведения о конфигурации"
|
||||
search="Поиск"
|
||||
usb="USB"
|
||||
windows_update="Центр обновления Windows"
|
||||
windows_defender="Безопасность Windows"
|
||||
apps="Приложения"
|
||||
apps_features="Установленные приложения"
|
||||
default_apps="Приложения по умолчанию"
|
||||
optional_features="Дополнительные компоненты"
|
||||
startup="Автозагрузка"
|
||||
personalization="Персонализация"
|
||||
lockscreen="Экран блокировки"
|
||||
background="Фон"
|
||||
colors="Цвета"
|
||||
themes="Темы"
|
||||
start="Пуск"
|
||||
taskbar="Панель задач"
|
||||
network="Сеть"
|
||||
status="Сеть и Интернет"
|
||||
ethernet="Ethernet"
|
||||
wifi="Wi-Fi"
|
||||
connections="Сетевые подключения"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="Приложения"
|
||||
paint="Paint"
|
||||
edge="Edge"
|
||||
calculator="Калькулятор"
|
||||
windows="Windows"
|
||||
cascade_windows="Отобразить окна каскадом"
|
||||
Show_windows_stacked="Отобразить окна стопкой"
|
||||
Show_windows_side_by_side="Отобразить окна в ряд"
|
||||
minimize_all_windows="Свернуть все окна"
|
||||
restore_all_windows="Восстановить все окна"
|
||||
task_manager="Диспетчер задач"
|
||||
taskbar_Settings="Параметры панели задач"
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
Slovenian
|
||||
by: github.com/anderlli0053
|
||||
*/
|
||||
|
||||
xxx="Dobrodošli v slovenščini"
|
||||
// shell.nss
|
||||
pin_unpin="Pripni/Odpni"
|
||||
|
||||
// develop.nss
|
||||
develop="&Razvijaj"
|
||||
editors="uredniki"
|
||||
windows_notepad="Beležnica za Windows"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="Upravljanje datotek"
|
||||
copy_multiple_paths='Kopiraj izbrane elemente (@sel.count)'
|
||||
all="Vse"
|
||||
invert="Obrni izbor"
|
||||
none="Nič"
|
||||
change_extension="Spremeni končnico datoteke"
|
||||
take_ownership="Prevzemi lastništvo"
|
||||
show_hide="Pokaži/Skrij"
|
||||
system_files="Sistemske datoteke"
|
||||
file_name_extensions="Pripone imen datotek"
|
||||
attributes="Atributi"
|
||||
register_server="Registracija strežnika"
|
||||
register="Registriraj"
|
||||
unregister="Deregistriraj"
|
||||
hidden="Skrito"
|
||||
system="Sistemsko"
|
||||
readonly="Samo za branje"
|
||||
archive="Arhiv"
|
||||
created="Ustvarjeno"
|
||||
modified="Spremenjeno"
|
||||
accessed="Dostopano"
|
||||
new_folder="Nov imenik"
|
||||
new_file="Nova datoteka"
|
||||
datetime="Datum in čas"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
folder="Imenik"
|
||||
all_control_panel_items="Vsi elementi nadzorne plošče"
|
||||
system="Sistem"
|
||||
about="O"
|
||||
your_info="Vaši podatki"
|
||||
system_info="Informacije o sistemu"
|
||||
search="Išči"
|
||||
usb="USB"
|
||||
windows_update="Windows Update"
|
||||
windows_defender="Windows Defender"
|
||||
apps="Aplikacije"
|
||||
apps_features="Funkcije aplikacij"
|
||||
default_apps="Privzete aplikacije"
|
||||
optional_features="Izbirne funkcije"
|
||||
startup="Zagon"
|
||||
personalization="Prilagajanje"
|
||||
lockscreen="Zaklenjen zaslon"
|
||||
background="Ozadje"
|
||||
colors="Barve"
|
||||
themes="Teme"
|
||||
start="Start"
|
||||
taskbar="Opravilna vrstica"
|
||||
network="Omrežje"
|
||||
status="Stanje"
|
||||
ethernet="Ethernet"
|
||||
wifi="WLAN"
|
||||
connections="Povezave"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="Aplikacije"
|
||||
paint="Slikar"
|
||||
edge="Edge"
|
||||
calculator="Kalkulator"
|
||||
windows="windows"
|
||||
cascade_windows="Okna v kaskado"
|
||||
Show_windows_stacked="Prikaži okna v nakladu"
|
||||
Show_windows_side_by_side="Prikaži okna eno ob drugem"
|
||||
minimize_all_windows="Minimiziraj vsa okna"
|
||||
restore_all_windows="Obnovi vsa okna"
|
||||
task_manager="Upravitelj opravil"
|
||||
taskbar_Settings="Nastavitve opravilne vrstice"
|
||||
@@ -0,0 +1,83 @@
|
||||
/*
|
||||
Türkçe
|
||||
by: Muha Aliss <muhaaliss@pm.me>
|
||||
*/
|
||||
|
||||
xxx="Türkçe hoş geldiniz"
|
||||
// shell.nss
|
||||
pin_unpin="Sabitle/Kaldır"
|
||||
|
||||
// develop.nss
|
||||
develop="&Geliştirici"
|
||||
editors="düzenleyiciler"
|
||||
windows_notepad="Windows not defteri"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="Dosya yönetimi"
|
||||
copy_multiple_paths="(@sel.count) öğe seçildi, kopyala"
|
||||
all="Tümü"
|
||||
invert="Ters çevir"
|
||||
none="Hiçbiri"
|
||||
change_extension="Uzantıyı değiştir"
|
||||
take_ownership="Sahipliği al"
|
||||
show_hide="Göster/Gizle"
|
||||
system_files="Sistem dosyaları"
|
||||
file_name_extensions="Dosya adı uzantıları"
|
||||
attributes="Özellikler"
|
||||
register_server="Sunucuyu kaydet"
|
||||
register="Kaydet"
|
||||
unregister="Kaydı kaldır"
|
||||
hidden="Gizli"
|
||||
system="Sistem"
|
||||
readonly="Salt okunur"
|
||||
archive="Arşiv"
|
||||
created="Oluşturulma"
|
||||
modified="Değiştirilme"
|
||||
accessed="Erişim"
|
||||
new_folder="Yeni Klasör"
|
||||
new_file="Yeni Dosya"
|
||||
datetime="TarihSaat"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
folder="Klasör"
|
||||
all_control_panel_items="Tüm Denetim Masası Öğeleri"
|
||||
system="Sistem"
|
||||
about="Hakkında"
|
||||
your_info="Bilgileriniz"
|
||||
system_info="Sistem Bilgisi"
|
||||
search="Ara"
|
||||
usb="USB"
|
||||
windows_update="Windows Güncelleme"
|
||||
windows_defender="Windows Defender"
|
||||
apps="Uygulamalar"
|
||||
apps_features="Uygulama Özellikleri"
|
||||
default_apps="Varsayılan Uygulamalar"
|
||||
optional_features="İsteğe Bağlı Özellikler"
|
||||
startup="Başlangıç"
|
||||
personalization="Kişiselleştirme"
|
||||
lockscreen="Kilit ekranı"
|
||||
background="Arka plan"
|
||||
colors="Renkler"
|
||||
themes="Temalar"
|
||||
start="Başlat"
|
||||
taskbar="Görev çubuğu"
|
||||
network="Ağ"
|
||||
status="Durum"
|
||||
ethernet="Ethernet"
|
||||
wifi="WLAN"
|
||||
connections="Bağlantılar"
|
||||
|
||||
// taskbar.nss
|
||||
apps="Uygulamalar"
|
||||
paint="Paint"
|
||||
edge="Edge"
|
||||
calculator="Hesap Makinesi"
|
||||
windows="pencereler"
|
||||
cascade_windows="Pencereleri kademeli göster"
|
||||
show_windows_stacked="Pencereleri yığılmış göster"
|
||||
show_windows_side_by_side="Pencereleri yan yana göster"
|
||||
minimize_all_windows="Tüm pencereleri simge durumuna küçült"
|
||||
restore_all_windows="Tüm pencereleri geri yükle"
|
||||
task_manager="Görev Yöneticisi"
|
||||
taskbar_settings="Görev Çubuğu Ayarları"
|
||||
@@ -0,0 +1,85 @@
|
||||
/*
|
||||
Ukrainian
|
||||
by: github.com/Silletr
|
||||
*/
|
||||
|
||||
|
||||
xxx="Ласкаво просимо!"
|
||||
// shell.nss
|
||||
pin_unpin="Закріпити/Відкріпити"
|
||||
|
||||
// develop.nss
|
||||
develop="&Розробка"
|
||||
editors="Редактори"
|
||||
windows_notepad="Блокнот"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="Файловий менеджер"
|
||||
copy_multiple_paths='Скопіювати шляхи до обраних елементів (@sel.count)'
|
||||
all="Усе"
|
||||
invert="Інвертувати виділення"
|
||||
none="Нічого"
|
||||
change_extension="Змінити розширення"
|
||||
take_ownership="Стати власником"
|
||||
show_hide="Показати/Приховати"
|
||||
system_files="Системніфайли"
|
||||
file_name_extensions="Показ файлових розширень"
|
||||
attributes="Атрибути"
|
||||
register_server="Зареєструвати сервер"
|
||||
register="Зареєструватись"
|
||||
unregister="Скасувати реєстрацію"
|
||||
hidden="Захований"
|
||||
system="Системний"
|
||||
readonly="Тільки для читання"
|
||||
archive="Архів"
|
||||
created="Створено"
|
||||
modified="Модифіковано"
|
||||
accessed="Доступ надано"
|
||||
new_folder="Нова папка"
|
||||
new_file="Новий файл"
|
||||
datetime="Имя: Дата і час"
|
||||
guid="Имя: Ідентифікатор GUID"
|
||||
|
||||
// goto.nss
|
||||
folder="Папки"
|
||||
all_control_panel_items="Усі елементи панелі керування"
|
||||
system="Системне"
|
||||
about="Про систему"
|
||||
your_info="Інформація про Вас"
|
||||
system_info="Інформація про систему"
|
||||
search="Пошук"
|
||||
usb="USB"
|
||||
windows_update="Центр оновлення Windows"
|
||||
windows_defender="Безпека Windows"
|
||||
apps="Додатки"
|
||||
apps_features="Завантажені додатки"
|
||||
default_apps="Додатки за замовчуванням"
|
||||
optional_features="Додаткові функції"
|
||||
startup="Автозапуск"
|
||||
personalization="Персонализація"
|
||||
lockscreen="Екран блокування"
|
||||
background="Фон"
|
||||
colors="Кольори"
|
||||
themes="Теми"
|
||||
start="Пуск"
|
||||
taskbar="Панель задач"
|
||||
network="Мережа"
|
||||
status="Мережа та Інтернет"
|
||||
ethernet="Ethernet"
|
||||
wifi="Wi-Fi"
|
||||
connections="Мережеві з'єднання"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="Додатки"
|
||||
paint="Paint"
|
||||
edge="Edge"
|
||||
calculator="Калькулятор"
|
||||
windows="Windows"
|
||||
cascade_windows="Показати всі вікна каскадом"
|
||||
Show_windows_stacked="Показати всі вікна"
|
||||
Show_windows_side_by_side="Відобразити вікна в ряд"
|
||||
minimize_all_windows="Згорнути всі вікна"
|
||||
restore_all_windows="Відновити всі вікна"
|
||||
task_manager="Диспетчер задач"
|
||||
taskbar_Settings="Параметри панелі задач"
|
||||
@@ -0,0 +1,85 @@
|
||||
/*
|
||||
Simplified Chinese
|
||||
by: github.com/JohnsonRan
|
||||
github.com/XY0797
|
||||
*/
|
||||
|
||||
xxx="欢迎用中文"
|
||||
// shell.nss
|
||||
pin_unpin="固定/取消固定"
|
||||
|
||||
// develop.nss
|
||||
develop="开发"
|
||||
editors="编辑器"
|
||||
windows_notepad="Windows 记事本"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="文件管理"
|
||||
copy_multiple_paths='复制选中的 (@sel.count) 个项目'
|
||||
all="全选"
|
||||
invert="反选"
|
||||
none="全不选"
|
||||
change_extension="更改扩展名"
|
||||
take_ownership="更改所有权"
|
||||
show_hide="显示/隐藏"
|
||||
system_files="系统文件"
|
||||
file_name_extensions="文件扩展名"
|
||||
attributes="属性"
|
||||
register_server="注册服务"
|
||||
register="注册"
|
||||
unregister="取消注册"
|
||||
hidden="隐藏"
|
||||
system="系统"
|
||||
readonly="只读"
|
||||
archive="存档"
|
||||
created="创建时间"
|
||||
modified="修改时间"
|
||||
accessed="访问时间"
|
||||
new_folder="新建文件夹"
|
||||
new_file="新建文件"
|
||||
datetime="当前时间"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
folder="文件夹"
|
||||
all_control_panel_items="所有控制面板项"
|
||||
system="系统"
|
||||
about="系统信息"
|
||||
your_info="账户信息"
|
||||
system_info="系统信息(CMD)"
|
||||
search="搜索"
|
||||
usb="USB"
|
||||
windows_update="Windows 更新"
|
||||
windows_defender="Windows 安全中心"
|
||||
apps="应用"
|
||||
apps_features="安装的应用"
|
||||
default_apps="默认应用"
|
||||
optional_features="可选功能"
|
||||
startup="启动"
|
||||
personalization="个性化"
|
||||
lockscreen="锁屏界面"
|
||||
background="背景"
|
||||
colors="颜色"
|
||||
themes="主题"
|
||||
start="开始"
|
||||
taskbar="任务栏"
|
||||
network="网络"
|
||||
status="网络和 Internet"
|
||||
ethernet="以太网"
|
||||
wifi="WLAN"
|
||||
connections="网络连接"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="应用"
|
||||
paint="画图"
|
||||
edge="Edge"
|
||||
calculator="计算器"
|
||||
windows="窗口"
|
||||
cascade_windows="层叠窗口"
|
||||
Show_windows_stacked="堆叠窗口"
|
||||
Show_windows_side_by_side="并排窗口"
|
||||
minimize_all_windows="最小化所有窗口"
|
||||
restore_all_windows="还原所有窗口"
|
||||
task_manager="任务管理器"
|
||||
taskbar_Settings="任务栏设置"
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
Traditional Chinese
|
||||
by: github.com/Eddie40802
|
||||
*/
|
||||
|
||||
xxx="歡迎使用繁體中文"
|
||||
// shell.nss
|
||||
pin_unpin="固定/取消固定"
|
||||
|
||||
// develop.nss
|
||||
develop="開發"
|
||||
editors="編輯器"
|
||||
windows_notepad="Windows 記事本"
|
||||
|
||||
// file-manage.nss
|
||||
file_manage="檔案管理"
|
||||
copy_multiple_paths='複製選中的 (@sel.count) 個項目'
|
||||
all="全選"
|
||||
invert="反向選擇"
|
||||
none="全部不選"
|
||||
change_extension="更改副檔名"
|
||||
take_ownership="更改所有權"
|
||||
show_hide="顯示/隱藏"
|
||||
system_files="系統檔案"
|
||||
file_name_extensions="檔案副檔名"
|
||||
attributes="屬性"
|
||||
register_server="註冊服務"
|
||||
register="註冊"
|
||||
unregister="取消註冊"
|
||||
hidden="隱藏"
|
||||
system="系統"
|
||||
readonly="唯讀"
|
||||
archive="封存"
|
||||
created="建立時間"
|
||||
modified="修改時間"
|
||||
accessed="存取時間"
|
||||
new_folder="新增資料夾"
|
||||
new_file="新增檔案"
|
||||
datetime="當前時間"
|
||||
guid="Guid"
|
||||
|
||||
// goto.nss
|
||||
folder="資料夾"
|
||||
all_control_panel_items="所有控制台項目"
|
||||
system="系統"
|
||||
about="系統資訊"
|
||||
your_info="帳戶資訊"
|
||||
system_info="系統資訊(命令提示字元)"
|
||||
search="搜尋"
|
||||
usb="USB"
|
||||
windows_update="Windows 更新"
|
||||
windows_defender="Windows Update"
|
||||
apps="應用程式"
|
||||
apps_features="已安裝的應用程式"
|
||||
default_apps="預設應用程式"
|
||||
optional_features="選用功能"
|
||||
startup="啟動"
|
||||
personalization="個人化"
|
||||
lockscreen="鎖定畫面"
|
||||
background="背景"
|
||||
colors="色彩"
|
||||
themes="佈景主題"
|
||||
start="開始"
|
||||
taskbar="工作列"
|
||||
network="網路"
|
||||
status="網路和網際網路"
|
||||
ethernet="乙太網路"
|
||||
wifi="WLAN"
|
||||
connections="網路連線"
|
||||
|
||||
|
||||
// taskbar.nss
|
||||
apps="應用程式"
|
||||
paint="小畫家"
|
||||
edge="Edge"
|
||||
calculator="小算盤"
|
||||
windows="視窗"
|
||||
cascade_windows="階梯式視窗"
|
||||
Show_windows_stacked="堆疊視窗"
|
||||
Show_windows_side_by_side="並排視窗"
|
||||
minimize_all_windows="最小化所有視窗"
|
||||
restore_all_windows="還原所有視窗"
|
||||
task_manager="工作管理員"
|
||||
taskbar_Settings="工作列設定"
|
||||
@@ -0,0 +1,34 @@
|
||||
// modify items
|
||||
// Remove items by identifiers
|
||||
modify(mode=mode.multiple
|
||||
where=this.id(id.restore_previous_versions,id.cast_to_device)
|
||||
vis=vis.remove)
|
||||
|
||||
modify(type="recyclebin" where=window.is_desktop and this.id==id.empty_recycle_bin pos=1 sep)
|
||||
|
||||
modify(find="unpin*" pos="bottom" menu="Pin/Unpin")
|
||||
modify(find="pin*" pos="top" menu="Pin/Unpin")
|
||||
|
||||
modify(where=this.id==id.copy_as_path menu="file manage")
|
||||
modify(type="dir.back|drive.back" where=this.id==id.customize_this_folder pos=1 sep="top" menu="file manage")
|
||||
|
||||
modify(where=str.equals(this.name, ["open in terminal", "open linux shell here"]) || this.id==id.open_powershell_window_here
|
||||
pos="bottom" menu="Terminal")
|
||||
|
||||
modify(mode=mode.multiple
|
||||
where=this.id(
|
||||
id.send_to,
|
||||
id.share,
|
||||
id.create_shortcut,
|
||||
id.set_as_desktop_background,
|
||||
id.rotate_left,
|
||||
id.rotate_right,
|
||||
id.map_network_drive,
|
||||
id.disconnect_network_drive,
|
||||
id.format,
|
||||
id.eject,
|
||||
id.give_access_to,
|
||||
id.include_in_library,
|
||||
id.print
|
||||
)
|
||||
pos=1 menu=title.more_options)
|
||||
@@ -0,0 +1,33 @@
|
||||
menu(type="taskbar" vis=key.shift() or key.lbutton() pos=0 title=app.name image=\uE249)
|
||||
{
|
||||
item(title="config" image=\uE10A cmd='"@app.cfg"')
|
||||
item(title="manager" image=\uE0F3 admin cmd='"@app.exe"')
|
||||
item(title="directory" image=\uE0E8 cmd='"@app.dir"')
|
||||
item(title="version\t"+@app.ver vis=label col=1)
|
||||
item(title="docs" image=\uE1C4 cmd='https://nilesoft.org/docs')
|
||||
item(title="donate" image=\uE1A7 cmd='https://nilesoft.org/donate')
|
||||
}
|
||||
menu(where=@(this.count == 0) type="taskbar" image=icon.settings expanded=true)
|
||||
{
|
||||
menu(title=loc.apps image=\uE254)
|
||||
{
|
||||
item(title=loc.paint image=\uE116 cmd='mspaint')
|
||||
item(title=loc.edge image cmd='@sys.prog32\Microsoft\Edge\Application\msedge.exe')
|
||||
item(title=loc.calculator image=\ue1e7 cmd='calc.exe')
|
||||
item(title=str.res('regedit.exe,-16') image cmd='regedit.exe')
|
||||
}
|
||||
menu(title=loc.windows image=\uE1FB)
|
||||
{
|
||||
item(title=loc.cascade_windows cmd=command.cascade_windows)
|
||||
item(title=loc.Show_windows_stacked cmd=command.Show_windows_stacked)
|
||||
item(title=loc.Show_windows_side_by_side cmd=command.Show_windows_side_by_side)
|
||||
sep
|
||||
item(title=loc.minimize_all_windows cmd=command.minimize_all_windows)
|
||||
item(title=loc.restore_all_windows cmd=command.restore_all_windows)
|
||||
}
|
||||
item(title=title.desktop image=icon.desktop cmd=command.toggle_desktop)
|
||||
item(title=title.settings image=icon.settings(auto, image.color1) cmd='ms-settings:')
|
||||
item(title=loc.task_manager sep=both image=icon.task_manager cmd='taskmgr.exe')
|
||||
item(title=loc.taskbar_Settings sep=both image=inherit cmd='ms-settings:taskbar')
|
||||
item(vis=key.shift() title=title.exit_explorer cmd=command.restart_explorer)
|
||||
}
|
||||
@@ -0,0 +1,15 @@
|
||||
menu(type='*' where=(sel.count or wnd.is_taskbar or wnd.is_edit) title=title.terminal sep=sep.top image=icon.run_with_powershell)
|
||||
{
|
||||
$tip_run_admin=["\xE1A7 Press [SHIFT key] or [RIGHT-CLICK] to run " + this.title + " as administrator", tip.warning, 1.0]
|
||||
$has_admin=key.shift() or key.rbutton()
|
||||
|
||||
item(title=title.command_prompt tip=tip_run_admin admin=has_admin image cmd-prompt=`/K TITLE Command Prompt &ver& PUSHD "@sel.dir"`)
|
||||
item(title=title.windows_powershell admin=has_admin tip=tip_run_admin image cmd-ps=`-noexit -command Set-Location -Path '@sel.dir'`)
|
||||
item(where=package.exists("WindowsTerminal")
|
||||
title=title.Windows_Terminal
|
||||
tip=tip_run_admin
|
||||
admin=has_admin
|
||||
image='@package.path("WindowsTerminal")\WindowsTerminal.exe'
|
||||
cmd="wt.exe"
|
||||
arg=`-d "@sel.path\."`)
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
theme
|
||||
{
|
||||
name="modern"
|
||||
dark=auto
|
||||
background
|
||||
{
|
||||
color=auto
|
||||
opacity=auto
|
||||
effect=auto
|
||||
}
|
||||
image.align=2
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
MIT License
|
||||
|
||||
Copyright (c) 2024 Nilesoft
|
||||
|
||||
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||
of this software and associated documentation files (the "Software"), to deal
|
||||
in the Software without restriction, including without limitation the rights
|
||||
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||
copies of the Software, and to permit persons to whom the Software is
|
||||
furnished to do so, subject to the following conditions:
|
||||
|
||||
The above copyright notice and this permission notice shall be included in all
|
||||
copies or substantial portions of the Software.
|
||||
|
||||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
SOFTWARE.
|
||||
@@ -0,0 +1,30 @@
|
||||
Nilesoft Shell
|
||||
|
||||
[about]
|
||||
Shell is a powerful, lightweight extension for Windows File Explorer that gives the user a high level of control over the context menu to improve its performance.
|
||||
Compatible with Windows 7 or later.
|
||||
|
||||
[update]
|
||||
(*) If you are updating, please first uninstall/unregister previous version.
|
||||
|
||||
[donate]
|
||||
If you really love Shell and would like to see it continue to improve.
|
||||
https://nilesoft.org/donate
|
||||
|
||||
[support]
|
||||
https://nilesoft.org
|
||||
https://nilesoft.org/github
|
||||
support@nilesoft.org
|
||||
|
||||
[DISCLAIMER]
|
||||
THE SOFTWARE IS DISTRIBUTED "AS IS". NO WARRANTY OF ANY KIND IS
|
||||
EXPRESSED OR IMPLIED. YOU USE THE SOFTWARE AT YOUR OWN RISK. THE
|
||||
AUTHORS WILL NOT BE LIABLE FOR DATA LOSS, DAMAGES, LOSS OF PROFITS OR
|
||||
ANY OTHER KIND OF LOSS WHILE USING OR MISUSING THE SOFTWARE.
|
||||
|
||||
Copyright (C) 2024 Nilesoft Ltd.
|
||||
|
||||
[plutovg]
|
||||
Copyright (c) 2020 Nwutobo Samuel Ugochukwu
|
||||
https://github.com/sammycage/plutovg
|
||||
|
||||
@@ -0,0 +1,36 @@
|
||||
settings
|
||||
{
|
||||
priority=1
|
||||
exclude.where = !process.is_explorer
|
||||
showdelay = 200
|
||||
// Options to allow modification of system items
|
||||
modify.remove.duplicate=1
|
||||
tip.enabled=true
|
||||
}
|
||||
|
||||
// localization
|
||||
$loc_path='imports\lang\'
|
||||
import lang loc_path + "en.nss"
|
||||
import lang if(path.exists(loc_path + sys.lang + ".nss"),
|
||||
loc_path + sys.lang + ".nss",
|
||||
loc_path + "en.nss")
|
||||
|
||||
// or import lang 'imports/lang/en.nss'
|
||||
|
||||
import 'imports/theme.nss'
|
||||
import 'imports/images.nss'
|
||||
import 'imports/modify.nss'
|
||||
|
||||
menu(mode="multiple" title=loc.pin_unpin image=icon.pin)
|
||||
{
|
||||
}
|
||||
|
||||
menu(mode="multiple" title=title.more_options image=icon.more_options)
|
||||
{
|
||||
}
|
||||
|
||||
import 'imports/terminal.nss'
|
||||
import 'imports/file-manage.nss'
|
||||
import 'imports/develop.nss'
|
||||
import 'imports/goto.nss'
|
||||
import 'imports/taskbar.nss'
|
||||
@@ -0,0 +1,193 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup Label="ProjectConfigurations">
|
||||
<ProjectConfiguration Include="release|x64">
|
||||
<Configuration>release</Configuration>
|
||||
<Platform>x64</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="release|Win32">
|
||||
<Configuration>release</Configuration>
|
||||
<Platform>Win32</Platform>
|
||||
</ProjectConfiguration>
|
||||
<ProjectConfiguration Include="release|ARM64">
|
||||
<Configuration>release</Configuration>
|
||||
<Platform>ARM64</Platform>
|
||||
</ProjectConfiguration>
|
||||
</ItemGroup>
|
||||
<PropertyGroup Label="Globals">
|
||||
<VCProjectVersion>16.0</VCProjectVersion>
|
||||
<Keyword>Win32Proj</Keyword>
|
||||
<ProjectGuid>{BAF011AC-D5E9-42C5-BA26-BA6115A45DAC}</ProjectGuid>
|
||||
<CharacterSet>Unicode</CharacterSet>
|
||||
<WindowsTargetPlatformVersion>10.0</WindowsTargetPlatformVersion>
|
||||
<RootNamespace>Shell</RootNamespace>
|
||||
<ProjectName>dll</ProjectName>
|
||||
<TargetName>shell</TargetName>
|
||||
<TargetExt>.dll</TargetExt>
|
||||
<GenerateManifest>false</GenerateManifest>
|
||||
<OutDir>$(SolutionDir)bin\</OutDir>
|
||||
<IntDir>$(ProjectDir)obj\$(Configuration.ToLower())\</IntDir>
|
||||
<ConfigurationType>DynamicLibrary</ConfigurationType>
|
||||
<PlatformToolset>v143</PlatformToolset>
|
||||
<PreferredToolArchitecture>x64</PreferredToolArchitecture>
|
||||
<CodeAnalysisRuleSet>NativeRecommendedRules.ruleset</CodeAnalysisRuleSet>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
|
||||
<PropertyGroup Condition="'$(Configuration)'=='release'" Label="Configuration">
|
||||
<UseDebugLibraries>false</UseDebugLibraries>
|
||||
<WholeProgramOptimization>true</WholeProgramOptimization>
|
||||
</PropertyGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
|
||||
<ImportGroup Label="ExtensionSettings">
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="Shared">
|
||||
<Import Project="$(SolutionDir)shared\shared.vcxitems" Label="Shared" />
|
||||
</ImportGroup>
|
||||
<ImportGroup Label="PropertySheets">
|
||||
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
|
||||
<Import Project="$(SolutionDir)shared\VC-LTL.props" Condition="Exists('$(SolutionDir)shared\VC-LTL.props')" />
|
||||
</ImportGroup>
|
||||
<PropertyGroup Label="UserMacros" />
|
||||
<PropertyGroup>
|
||||
<LibraryPath>$(SolutionDir)shared\Library;$(LibraryPath)</LibraryPath>
|
||||
<IncludePath>$(ProjectDir)src;$(ProjectDir)src\include;$(IncludePath)</IncludePath>
|
||||
</PropertyGroup>
|
||||
<PropertyGroup Condition="'$(Configuration)'=='release'">
|
||||
<LinkIncremental>false</LinkIncremental>
|
||||
</PropertyGroup>
|
||||
<ItemDefinitionGroup Label="Globals">
|
||||
<ClCompile>
|
||||
<WarningLevel>Level4</WarningLevel>
|
||||
<SDLCheck>true</SDLCheck>
|
||||
<PreprocessorDefinitions>_WINDOWS;_WINDLL;_USRDLL;Shell_EXPORTS;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<ConformanceMode>true</ConformanceMode>
|
||||
<PrecompiledHeader>NotUsing</PrecompiledHeader>
|
||||
<PrecompiledHeaderFile>pch.h</PrecompiledHeaderFile>
|
||||
<PrecompiledHeaderOutputFile>$(IntDir)$(TargetName).pch</PrecompiledHeaderOutputFile>
|
||||
<LanguageStandard>stdcpp20</LanguageStandard>
|
||||
<CallingConvention>StdCall</CallingConvention>
|
||||
<ExceptionHandling>Async</ExceptionHandling>
|
||||
<RuntimeTypeInfo>false</RuntimeTypeInfo>
|
||||
<CompileAsManaged>false</CompileAsManaged>
|
||||
<FunctionLevelLinking>true</FunctionLevelLinking>
|
||||
<TreatWarningAsError>false</TreatWarningAsError>
|
||||
<TreatWChar_tAsBuiltInType>true</TreatWChar_tAsBuiltInType>
|
||||
<LanguageStandard_C>stdc17</LanguageStandard_C>
|
||||
<MultiProcessorCompilation>true</MultiProcessorCompilation>
|
||||
<EnableParallelCodeGeneration>true</EnableParallelCodeGeneration>
|
||||
<GenerateModuleDependencies>false</GenerateModuleDependencies>
|
||||
<ScanSourceForModuleDependencies>false</ScanSourceForModuleDependencies>
|
||||
<GenerateSourceDependencies>false</GenerateSourceDependencies>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<SubSystem>Windows</SubSystem>
|
||||
<MinimumRequiredVersion>6.1</MinimumRequiredVersion>
|
||||
<ModuleDefinitionFile>src\$(TargetName).def</ModuleDefinitionFile>
|
||||
<OutputFile>$(OutDir)$(TargetName)$(TargetExt)</OutputFile>
|
||||
<ProgramDatabaseFile>$(OutDir)$(TargetName)$(TargetExt).pdb</ProgramDatabaseFile>
|
||||
<ProfileGuidedDatabase>$(OutDir)$(TargetName)$(TargetExt).pgd</ProfileGuidedDatabase>
|
||||
<AdditionalDependencies>kernel32.lib;user32.lib;gdi32.lib;advapi32.lib;shell32.lib;ole32.lib</AdditionalDependencies>
|
||||
</Link>
|
||||
<ResourceCompile>
|
||||
<Culture>0x0409</Culture>
|
||||
<PreprocessorDefinitions>_WINDLL;_WIN64;_UNICODE;UNICODE;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
</ResourceCompile>
|
||||
<Xdcmake>
|
||||
<OutputFile>$(OutDir)$(TargetName)$(TargetExt).xml</OutputFile>
|
||||
</Xdcmake>
|
||||
<Bscmake>
|
||||
<OutputFile>$(OutDir)$(TargetName)$(TargetExt).bsc</OutputFile>
|
||||
</Bscmake>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Configuration)'=='release'">
|
||||
<ClCompile>
|
||||
<IntrinsicFunctions>true</IntrinsicFunctions>
|
||||
<PreprocessorDefinitions>NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>
|
||||
<RuntimeLibrary>MultiThreaded</RuntimeLibrary>
|
||||
<DebugInformationFormat>None</DebugInformationFormat>
|
||||
<WholeProgramOptimization>false</WholeProgramOptimization>
|
||||
<FavorSizeOrSpeed>Speed</FavorSizeOrSpeed>
|
||||
<Optimization>MaxSpeed</Optimization>
|
||||
<EnableModules>false</EnableModules>
|
||||
<CreateHotpatchableImage>false</CreateHotpatchableImage>
|
||||
</ClCompile>
|
||||
<Link>
|
||||
<EnableCOMDATFolding>true</EnableCOMDATFolding>
|
||||
<OptimizeReferences>false</OptimizeReferences>
|
||||
<GenerateDebugInformation>false</GenerateDebugInformation>
|
||||
<LinkTimeCodeGeneration>Default</LinkTimeCodeGeneration>
|
||||
<IgnoreEmbeddedIDL>true</IgnoreEmbeddedIDL>
|
||||
<AdditionalOptions>/DEBUG:NONE /EMITPOGOPHASEINFO</AdditionalOptions>
|
||||
<SetChecksum>true</SetChecksum>
|
||||
<IgnoreSpecificDefaultLibraries />
|
||||
<ImageHasSafeExceptionHandlers />
|
||||
</Link>
|
||||
<Xdcmake>
|
||||
<SuppressStartupBanner Condition="'$(Configuration)|$(Platform)'=='release|x64'">false</SuppressStartupBanner>
|
||||
</Xdcmake>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemDefinitionGroup Condition="'$(Platform)'=='ARM64'">
|
||||
<Link>
|
||||
<MinimumRequiredVersion>10.0</MinimumRequiredVersion>
|
||||
</Link>
|
||||
</ItemDefinitionGroup>
|
||||
<ItemGroup>
|
||||
<None Include="packages.config" />
|
||||
<None Include="readme.txt" />
|
||||
<None Include="src\Shell.def" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="src\Expression\ArrayExpression.h" />
|
||||
<ClInclude Include="src\Expression\Constants.h" />
|
||||
<ClInclude Include="src\Expression\Context.h" />
|
||||
<ClInclude Include="src\Expression\ExpressionType.h" />
|
||||
<ClInclude Include="src\Expression\IdentExpression.h" />
|
||||
<ClInclude Include="src\Expression\OperatorExpression.h" />
|
||||
<ClInclude Include="src\Expression\Scope.h" />
|
||||
<ClInclude Include="src\Expression\StatementExpression.h" />
|
||||
<ClInclude Include="src\Expression\LiteralExpression.h" />
|
||||
<ClInclude Include="src\Expression\Variable.h" />
|
||||
<ClInclude Include="src\Include\Cache.h" />
|
||||
<ClInclude Include="src\Include\RegistryConfig.h" />
|
||||
<ClInclude Include="src\Include\Theme.h" />
|
||||
<ClInclude Include="src\Include\Keyboard.h" />
|
||||
<ClInclude Include="src\Include\Styles.h" />
|
||||
<ClInclude Include="src\Include\Tip.h" />
|
||||
<ClInclude Include="src\Include\UTheme.h" />
|
||||
<ClInclude Include="src\Include\win32_hook.h" />
|
||||
<ClInclude Include="src\Parser\IdentHash.h" />
|
||||
<ClInclude Include="src\Parser\Lexer.h" />
|
||||
<ClInclude Include="src\pch.h" />
|
||||
<ClInclude Include="src\Include\Hooker.h" />
|
||||
<ClInclude Include="src\Include\Initializer.h" />
|
||||
<ClInclude Include="src\Include\Menu.h" />
|
||||
<ClInclude Include="src\Include\MenuItem.h" />
|
||||
<ClInclude Include="src\Include\Selections.h" />
|
||||
<ClInclude Include="src\Include\ContextMenu.h" />
|
||||
<ClInclude Include="src\Parser\Ident.h" />
|
||||
<ClInclude Include="src\Expression\Expression.h" />
|
||||
<ClInclude Include="src\Parser\Parser.h" />
|
||||
<ClInclude Include="src\Parser\Token.h" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="src\Expression\ArrayExpression.cpp" />
|
||||
<ClCompile Include="src\Expression\Context.cpp" />
|
||||
<ClCompile Include="src\Expression\FuncExpression.cpp" />
|
||||
<ClCompile Include="src\Expression\Expression.cpp" />
|
||||
<ClCompile Include="src\Expression\OperatorExpression.cpp" />
|
||||
<ClCompile Include="src\Expression\Scope.cpp" />
|
||||
<ClInclude Include="src\Include\FindPattern.h" />
|
||||
<ClCompile Include="src\Parser\Lexer.cpp" />
|
||||
<ClCompile Include="src\Parser\Properties.cpp" />
|
||||
<ClCompile Include="src\Parser\Verification.cpp" />
|
||||
<ClCompile Include="src\Parser\Parser.cpp" />
|
||||
<ClCompile Include="src\Selections.cpp" />
|
||||
<ClCompile Include="src\ContextMenu.cpp" />
|
||||
<ClCompile Include="src\Main.cpp" />
|
||||
<ClCompile Include="src\Initializer.cpp" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="$(SolutionDir)shared\Resource\Shell.rc" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
|
||||
</Project>
|
||||
@@ -0,0 +1,188 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<ItemGroup>
|
||||
<Filter Include="Source Files">
|
||||
<UniqueIdentifier>{4FC737F1-C7A5-4376-A066-2A32D752A2FF}</UniqueIdentifier>
|
||||
<Extensions>cpp;c;cc;cxx;def;odl;idl;hpj;bat;asm;asmx</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Header Files">
|
||||
<UniqueIdentifier>{93995380-89BD-4b04-88EB-625FBE52EBFB}</UniqueIdentifier>
|
||||
<Extensions>h;hpp;hxx;hm;inl;inc;xsd</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Resource Files">
|
||||
<UniqueIdentifier>{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}</UniqueIdentifier>
|
||||
<Extensions>rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx;tiff;tif;png;wav;mfcribbon-ms</Extensions>
|
||||
</Filter>
|
||||
<Filter Include="Others Files">
|
||||
<UniqueIdentifier>{d0e2ec49-fd34-4fbc-92d7-f7e4342b237b}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="Source Files\Parser">
|
||||
<UniqueIdentifier>{9231c71f-ce54-4952-9979-af5aab7f0847}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="Header Files\Parser">
|
||||
<UniqueIdentifier>{fecc6b83-f073-4167-8d12-a0972703de25}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="Header Files\Expression">
|
||||
<UniqueIdentifier>{ffa179b7-1865-42f1-9282-1be4ba223cd6}</UniqueIdentifier>
|
||||
</Filter>
|
||||
<Filter Include="Source Files\Expression">
|
||||
<UniqueIdentifier>{3b006c06-2267-447d-9adf-d639beae60f4}</UniqueIdentifier>
|
||||
</Filter>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<None Include="ReadMe.txt">
|
||||
<Filter>Others Files</Filter>
|
||||
</None>
|
||||
<None Include="src\Shell.def">
|
||||
<Filter>Others Files</Filter>
|
||||
</None>
|
||||
<None Include="packages.config" />
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClCompile Include="src\Main.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Parser\Parser.cpp">
|
||||
<Filter>Source Files\Parser</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Parser\Verification.cpp">
|
||||
<Filter>Source Files\Parser</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\ContextMenu.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Expression\Expression.cpp">
|
||||
<Filter>Source Files\Expression</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Expression\FuncExpression.cpp">
|
||||
<Filter>Source Files\Expression</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Selections.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Initializer.cpp">
|
||||
<Filter>Source Files</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Parser\Properties.cpp">
|
||||
<Filter>Source Files\Parser</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Expression\Context.cpp">
|
||||
<Filter>Source Files\Expression</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Expression\Scope.cpp">
|
||||
<Filter>Source Files\Expression</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Expression\OperatorExpression.cpp">
|
||||
<Filter>Source Files\Expression</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Parser\Lexer.cpp">
|
||||
<Filter>Source Files\Parser</Filter>
|
||||
</ClCompile>
|
||||
<ClCompile Include="src\Expression\ArrayExpression.cpp">
|
||||
<Filter>Source Files\Expression</Filter>
|
||||
</ClCompile>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ClInclude Include="src\pch.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Parser\Ident.h">
|
||||
<Filter>Header Files\Parser</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Parser\Parser.h">
|
||||
<Filter>Header Files\Parser</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Parser\Token.h">
|
||||
<Filter>Header Files\Parser</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\Menu.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\MenuItem.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\ContextMenu.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\Styles.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\Expression.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\Scope.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Parser\IdentHash.h">
|
||||
<Filter>Header Files\Parser</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\win32_hook.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\Selections.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\Initializer.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\Hooker.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\Context.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\Cache.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\ExpressionType.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\StatementExpression.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\OperatorExpression.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\IdentExpression.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\LiteralExpression.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\FindPattern.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\Keyboard.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\Constants.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Parser\Lexer.h">
|
||||
<Filter>Header Files\Parser</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\ArrayExpression.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Expression\Variable.h">
|
||||
<Filter>Header Files\Expression</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\UTheme.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\Theme.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\Tip.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
<ClInclude Include="src\Include\RegistryConfig.h">
|
||||
<Filter>Header Files</Filter>
|
||||
</ClInclude>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
<ResourceCompile Include="$(SolutionDir)shared\Resource\Shell.rc">
|
||||
<Filter>Resource Files</Filter>
|
||||
</ResourceCompile>
|
||||
</ItemGroup>
|
||||
</Project>
|
||||
@@ -0,0 +1,6 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<Project ToolsVersion="Current" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||
<PropertyGroup>
|
||||
<ShowAllFiles>false</ShowAllFiles>
|
||||
</PropertyGroup>
|
||||
</Project>
|
||||
@@ -0,0 +1,4 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<packages>
|
||||
<package id="VC-LTL" version="5.1.1" targetFramework="native" />
|
||||
</packages>
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,62 @@
|
||||
#include <pch.h>
|
||||
|
||||
#include "Expression\Constants.h"
|
||||
#include "Expression\Variable.h"
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
Expression *ArrayExpression::get(size_t index)
|
||||
{
|
||||
if(index < expressions.size())
|
||||
return expressions[index];
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void ArrayExpression::push_back(Expression *e)
|
||||
{
|
||||
if(e)
|
||||
{
|
||||
e->Parent = this;
|
||||
expressions.push_back(e);
|
||||
}
|
||||
}
|
||||
|
||||
void ArrayExpression::push_back(std::unique_ptr<Expression> &&e)
|
||||
{
|
||||
if(e)
|
||||
{
|
||||
e->Parent = this;
|
||||
expressions.push_back(e.release());
|
||||
}
|
||||
}
|
||||
|
||||
ExpressionType ArrayExpression::Type() const
|
||||
{
|
||||
return ExpressionType::Array;
|
||||
}
|
||||
|
||||
Expression *ArrayExpression::Copy()
|
||||
{
|
||||
std::unique_ptr<ArrayExpression> a(new ArrayExpression(Parent));
|
||||
for(auto e : expressions) a->push_back(e->Copy());
|
||||
return a.release();
|
||||
}
|
||||
|
||||
Object ArrayExpression::Eval(Context *context)
|
||||
{
|
||||
auto array = new Object[expressions.size() + 1];
|
||||
Object result(array, true);
|
||||
*array++ = expressions.size();
|
||||
for(auto &e : expressions)
|
||||
{
|
||||
try{
|
||||
*array++ = context->Eval(e).move();
|
||||
}
|
||||
catch(...) {}
|
||||
}
|
||||
return result.move();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
class ArrayExpression : public Expression
|
||||
{
|
||||
private:
|
||||
std::vector<Expression *> expressions;
|
||||
|
||||
public:
|
||||
ArrayExpression(Expression *parent = nullptr) { Parent = parent; }
|
||||
virtual ~ArrayExpression() { for(auto e : expressions) delete e; }
|
||||
|
||||
ExpressionType Type() const override;
|
||||
Expression *Copy() override;
|
||||
Object Eval(Context *context) override;
|
||||
|
||||
Expression *get(size_t index);
|
||||
bool size() const { return expressions.size(); }
|
||||
bool empty() const { return expressions.empty(); }
|
||||
void push_back(Expression *e);
|
||||
void push_back(std::unique_ptr<Expression> &&e);
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,250 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
const std::tuple<uint32_t, int> MSG_FLAGS[] =
|
||||
{
|
||||
{ IDENT_MSG_ERROR, MB_ICONERROR},
|
||||
{ IDENT_MSG_QUESTION, MB_ICONQUESTION},
|
||||
{ IDENT_MSG_WARNING, MB_ICONWARNING},
|
||||
{ IDENT_MSG_INFO, MB_ICONINFORMATION},
|
||||
{ IDENT_MSG_OK, MB_OK},
|
||||
{ IDENT_MSG_OKCANCEL, MB_OKCANCEL},
|
||||
{ IDENT_MSG_YESNOCANCEL, MB_YESNOCANCEL},
|
||||
{ IDENT_MSG_YESNO, MB_YESNO},
|
||||
{ IDENT_MSG_IDCANCEL, IDCANCEL},
|
||||
{ IDENT_MSG_IDOK, IDOK},
|
||||
{ IDENT_MSG_IDYES, IDYES},
|
||||
{ IDENT_MSG_IDNO, IDNO},
|
||||
{ IDENT_MSG_RIGHT, IDNO},
|
||||
{ IDENT_MSG_RTLREADING, MB_RTLREADING},
|
||||
{ IDENT_MSG_SETFOREGROUND, MB_SETFOREGROUND},
|
||||
{ IDENT_MSG_TOPMOST, MB_TOPMOST},
|
||||
{ IDENT_MSG_APPLMODAL, MB_APPLMODAL},
|
||||
{ IDENT_MSG_TASKMODAL, MB_TASKMODAL},
|
||||
{ IDENT_MSG_DEFBUTTON1, MB_DEFBUTTON1},
|
||||
{ IDENT_MSG_DEFBUTTON2, MB_DEFBUTTON2},
|
||||
{ IDENT_MSG_DEFBUTTON3, MB_DEFBUTTON3}
|
||||
};
|
||||
|
||||
const std::tuple<uint32_t, COLORREF> ColorTable[] =
|
||||
{
|
||||
{IDENT_COLOR_DEFAULT, IDENT_COLOR_DEFAULT},
|
||||
{IDENT_COLOR_ACCENT, IDENT_COLOR_ACCENT},
|
||||
{IDENT_COLOR_ACCENT_LIGHT1, IDENT_COLOR_ACCENT_LIGHT1},
|
||||
{IDENT_COLOR_ACCENT_LIGHT2, IDENT_COLOR_ACCENT_LIGHT2},
|
||||
{IDENT_COLOR_ACCENT_LIGHT3, IDENT_COLOR_ACCENT_LIGHT3},
|
||||
{IDENT_COLOR_ACCENT_DARK1, IDENT_COLOR_ACCENT_DARK1},
|
||||
{IDENT_COLOR_ACCENT_DARK2, IDENT_COLOR_ACCENT_DARK2},
|
||||
{IDENT_COLOR_ACCENT_DARK3, IDENT_COLOR_ACCENT_DARK3},
|
||||
{IDENT_COLOR_BLACK, 0xFF000000},
|
||||
{IDENT_COLOR_WHITE, 0xFFFFFFFF},
|
||||
{IDENT_COLOR_ALICEBLUE, 0xFFF0F8FF},
|
||||
{IDENT_COLOR_ANTIQUEWHITE, 0xFFFAEBD7},
|
||||
{IDENT_COLOR_AQUA, 0xFF00FFFF},
|
||||
{IDENT_COLOR_AQUAMARINE, 0xFF7FFFD4},
|
||||
{IDENT_COLOR_AZURE, 0xFFF0FFFF},
|
||||
{IDENT_COLOR_BEIGE, 0xFFF5F5DC},
|
||||
{IDENT_COLOR_BISQUE, 0xFFFFE4C4},
|
||||
{IDENT_COLOR_BLANCHEDALMOND, 0xFFFFEBCD},
|
||||
{IDENT_COLOR_BLUE, 0xFF0000FF},
|
||||
{IDENT_COLOR_BLUEVIOLET, 0xFF8A2BE2},
|
||||
{IDENT_COLOR_BROWN, 0xFFA52A2A},
|
||||
{IDENT_COLOR_BURLYWOOD, 0xFFDEB887},
|
||||
{IDENT_COLOR_CADETBLUE, 0xFF5F9EA0},
|
||||
{IDENT_COLOR_CHARTREUSE, 0xFF7FFF00},
|
||||
{IDENT_COLOR_CHOCOLATE, 0xFFD2691E},
|
||||
{IDENT_COLOR_CORAL, 0xFFFF7F50},
|
||||
{IDENT_COLOR_CORNFLOWERBLUE, 0xFF6495ED},
|
||||
{IDENT_COLOR_CORNSILK, 0xFFFFF8DC},
|
||||
{IDENT_COLOR_CRIMSON, 0xFFDC143C},
|
||||
{IDENT_COLOR_CYAN, 0xFF00FFFF},
|
||||
{IDENT_COLOR_DARKBLUE, 0xFF00008B},
|
||||
{IDENT_COLOR_DARKCYAN, 0xFF008B8B},
|
||||
{IDENT_COLOR_DARKGOLDENROD, 0xFFB8860B},
|
||||
{IDENT_COLOR_DARKGRAY, 0xFFA9A9A9},
|
||||
{IDENT_COLOR_DARKGREEN, 0xFF006400},
|
||||
{IDENT_COLOR_DARKKHAKI, 0xFFBDB76B},
|
||||
{IDENT_COLOR_DARKMAGENTA, 0xFF8B008B},
|
||||
{IDENT_COLOR_DARKOLIVEGREEN, 0xFF556B2F},
|
||||
{IDENT_COLOR_DARKORANGE, 0xFFFF8C00},
|
||||
{IDENT_COLOR_DARKORCHID, 0xFF9932CC},
|
||||
{IDENT_COLOR_DARKRED, 0xFF8B0000},
|
||||
{IDENT_COLOR_DARKSALMON, 0xFFE9967A},
|
||||
{IDENT_COLOR_DARKSEAGREEN, 0xFF8FBC8F},
|
||||
{IDENT_COLOR_DARKSLATEBLUE, 0xFF483D8B},
|
||||
{IDENT_COLOR_DARKSLATEGRAY, 0xFF2F4F4F},
|
||||
{IDENT_COLOR_DARKTURQUOISE, 0xFF00CED1},
|
||||
{IDENT_COLOR_DARKVIOLET, 0xFF9400D3},
|
||||
{IDENT_COLOR_DEEPPINK, 0xFFFF1493},
|
||||
{IDENT_COLOR_DEEPSKYBLUE, 0xFF00BFFF},
|
||||
{IDENT_COLOR_DIMGRAY, 0xFF696969},
|
||||
{IDENT_COLOR_DODGERBLUE, 0xFF1E90FF},
|
||||
{IDENT_COLOR_FIREBRICK, 0xFFB22222},
|
||||
{IDENT_COLOR_FLORALWHITE, 0xFFFFFAF0},
|
||||
{IDENT_COLOR_FORESTGREEN, 0xFF228B22},
|
||||
{IDENT_COLOR_FUCHSIA, 0xFFFF00FF},
|
||||
{IDENT_COLOR_GAINSBORO, 0xFFDCDCDC},
|
||||
{IDENT_COLOR_GHOSTWHITE, 0xFFF8F8FF},
|
||||
{IDENT_COLOR_GOLD, 0xFFFFD700},
|
||||
{IDENT_COLOR_GOLDENROD, 0xFFDAA520},
|
||||
{IDENT_COLOR_GRAY, 0xFF808080},
|
||||
{IDENT_COLOR_GREEN, 0xFF008000},
|
||||
{IDENT_COLOR_GREENYELLOW, 0xFFADFF2F},
|
||||
{IDENT_COLOR_HONEYDEW, 0xFFF0FFF0},
|
||||
{IDENT_COLOR_HOTPINK, 0xFFFF69B4},
|
||||
{IDENT_COLOR_INDIANRED, 0xFFCD5C5C},
|
||||
{IDENT_COLOR_INDIGO, 0xFF4B0082},
|
||||
{IDENT_COLOR_IVORY, 0xFFFFFFF0},
|
||||
{IDENT_COLOR_KHAKI, 0xFFF0E68C},
|
||||
{IDENT_COLOR_LAVENDER, 0xFFE6E6FA},
|
||||
{IDENT_COLOR_LAVENDERBLUSH, 0xFFFFF0F5},
|
||||
{IDENT_COLOR_LAWNGREEN, 0xFF7CFC00},
|
||||
{IDENT_COLOR_LEMONCHIFFON, 0xFFFFFACD},
|
||||
{IDENT_COLOR_LIGHTBLUE, 0xFFADD8E6},
|
||||
{IDENT_COLOR_LIGHTCORAL, 0xFFF08080},
|
||||
{IDENT_COLOR_LIGHTCYAN, 0xFFE0FFFF},
|
||||
{IDENT_COLOR_LIGHTGOLDENRODYELLOW, 0xFFFAFAD2},
|
||||
{IDENT_COLOR_LIGHTGRAY, 0xFFD3D3D3},
|
||||
{IDENT_COLOR_LIGHTGREEN, 0xFF90EE90},
|
||||
{IDENT_COLOR_LIGHTPINK, 0xFFFFB6C1},
|
||||
{IDENT_COLOR_LIGHTSALMON, 0xFFFFA07A},
|
||||
{IDENT_COLOR_LIGHTSEAGREEN, 0xFF20B2AA},
|
||||
{IDENT_COLOR_LIGHTSKYBLUE, 0xFF87CEFA},
|
||||
{IDENT_COLOR_LIGHTSLATEGRAY, 0xFF778899},
|
||||
{IDENT_COLOR_LIGHTSTEELBLUE, 0xFFB0C4DE},
|
||||
{IDENT_COLOR_LIGHTYELLOW, 0xFFFFFFE0},
|
||||
{IDENT_COLOR_LIME, 0xFF00FF00},
|
||||
{IDENT_COLOR_LIMEGREEN, 0xFF32CD32},
|
||||
{IDENT_COLOR_LINEN, 0xFFFAF0E6},
|
||||
{IDENT_COLOR_MAGENTA, 0xFFFF00FF},
|
||||
{IDENT_COLOR_MAROON, 0xFF800000},
|
||||
{IDENT_COLOR_MEDIUMAQUAMARINE, 0xFF66CDAA},
|
||||
{IDENT_COLOR_MEDIUMBLUE, 0xFF0000CD},
|
||||
{IDENT_COLOR_MEDIUMORCHID, 0xFFBA55D3},
|
||||
{IDENT_COLOR_MEDIUMPURPLE, 0xFF9370DB},
|
||||
{IDENT_COLOR_MEDIUMSEAGREEN, 0xFF3CB371},
|
||||
{IDENT_COLOR_MEDIUMSLATEBLUE, 0xFF7B68EE},
|
||||
{IDENT_COLOR_MEDIUMSPRINGGREEN, 0xFF00FA9A},
|
||||
{IDENT_COLOR_MEDIUMTURQUOISE, 0xFF48D1CC},
|
||||
{IDENT_COLOR_MEDIUMVIOLETRED, 0xFFC71585},
|
||||
{IDENT_COLOR_MIDNIGHTBLUE, 0xFF191970},
|
||||
{IDENT_COLOR_MINTCREAM, 0xFFF5FFFA},
|
||||
{IDENT_COLOR_MISTYROSE, 0xFFFFE4E1},
|
||||
{IDENT_COLOR_MOCCASIN, 0xFFFFE4B5},
|
||||
{IDENT_COLOR_NAVAJOWHITE, 0xFFFFDEAD},
|
||||
{IDENT_COLOR_NAVY, 0xFF000080},
|
||||
{IDENT_COLOR_OLDLACE, 0xFFFDF5E6},
|
||||
{IDENT_COLOR_OLIVE, 0xFF808000},
|
||||
{IDENT_COLOR_OLIVEDRAB, 0xFF6B8E23},
|
||||
{IDENT_COLOR_ORANGE, 0xFFFFA500},
|
||||
{IDENT_COLOR_ORANGERED, 0xFFFF4500},
|
||||
{IDENT_COLOR_ORCHID, 0xFFDA70D6},
|
||||
{IDENT_COLOR_PALEGOLDENROD, 0xFFEEE8AA},
|
||||
{IDENT_COLOR_PALEGREEN, 0xFF98FB98},
|
||||
{IDENT_COLOR_PALETURQUOISE, 0xFFAFEEEE},
|
||||
{IDENT_COLOR_PALEVIOLETRED, 0xFFDB7093},
|
||||
{IDENT_COLOR_PAPAYAWHIP, 0xFFFFEFD5},
|
||||
{IDENT_COLOR_PEACHPUFF, 0xFFFFDAB9},
|
||||
{IDENT_COLOR_PERU, 0xFFCD853F},
|
||||
{IDENT_COLOR_PINK, 0xFFFFC0CB},
|
||||
{IDENT_COLOR_PLUM, 0xFFDDA0DD},
|
||||
{IDENT_COLOR_POWDERBLUE, 0xFFB0E0E6},
|
||||
{IDENT_COLOR_PURPLE, 0xFF800080},
|
||||
{IDENT_COLOR_RED, 0xFFFF0000},
|
||||
{IDENT_COLOR_ROSYBROWN, 0xFFBC8F8F},
|
||||
{IDENT_COLOR_ROYALBLUE, 0xFF4169E1},
|
||||
{IDENT_COLOR_SADDLEBROWN, 0xFF8B4513},
|
||||
{IDENT_COLOR_SALMON, 0xFFFA8072},
|
||||
{IDENT_COLOR_SANDYBROWN, 0xFFF4A460},
|
||||
{IDENT_COLOR_SEAGREEN, 0xFF2E8B57},
|
||||
{IDENT_COLOR_SEASHELL, 0xFFFFF5EE},
|
||||
{IDENT_COLOR_SIENNA, 0xFFA0522D},
|
||||
{IDENT_COLOR_SILVER, 0xFFC0C0C0},
|
||||
{IDENT_COLOR_SKYBLUE, 0xFF87CEEB},
|
||||
{IDENT_COLOR_SLATEBLUE, 0xFF6A5ACD},
|
||||
{IDENT_COLOR_SLATEGRAY, 0xFF708090},
|
||||
{IDENT_COLOR_SNOW, 0xFFFFFAFA},
|
||||
{IDENT_COLOR_SPRINGGREEN, 0xFF00FF7F},
|
||||
{IDENT_COLOR_STEELBLUE, 0xFF4682B4},
|
||||
{IDENT_COLOR_TAN, 0xFFD2B48C},
|
||||
{IDENT_COLOR_TEAL, 0xFF008080},
|
||||
{IDENT_COLOR_THISTLE, 0xFFD8BFD8},
|
||||
{IDENT_COLOR_TOMATO, 0xFFFF6347},
|
||||
{IDENT_COLOR_TRANSPARENT, 0x00FFFFFF},
|
||||
{IDENT_COLOR_TURQUOISE, 0xFF40E0D0},
|
||||
{IDENT_COLOR_VIOLET, 0xFFEE82EE},
|
||||
{IDENT_COLOR_WHEAT, 0xFFF5DEB3},
|
||||
{IDENT_COLOR_WHITESMOKE, 0xFFF5F5F5},
|
||||
{IDENT_COLOR_YELLOW, 0xFFFFFF00},
|
||||
{IDENT_COLOR_YELLOWGREEN, 0xFF9ACD32}
|
||||
};
|
||||
|
||||
const std::tuple<uint32_t, int> KeyTable[] =
|
||||
{
|
||||
{ IDENT_KEY_NONE, 0x00},
|
||||
{ IDENT_KEY_CONTROL, VK_CONTROL},
|
||||
{ IDENT_KEY_LCONTROL, VK_LCONTROL},
|
||||
{ IDENT_KEY_RCONTROL, VK_RCONTROL},
|
||||
{ IDENT_KEY_CTRL, VK_CONTROL},
|
||||
{ IDENT_KEY_RCTRL, VK_RCONTROL},
|
||||
{ IDENT_KEY_LCTRL, VK_LCONTROL},
|
||||
{ IDENT_KEY_ALT, VK_MENU},
|
||||
{ IDENT_KEY_LALT, VK_LMENU},
|
||||
{ IDENT_KEY_RALT, VK_RMENU},
|
||||
{ IDENT_KEY_SHIFT, VK_SHIFT},
|
||||
{ IDENT_KEY_RSHIFT, VK_RSHIFT},
|
||||
{ IDENT_KEY_LSHIFT, VK_LSHIFT},
|
||||
{ IDENT_KEY_WIN, VK_LWIN | VK_RWIN},
|
||||
{ IDENT_KEY_LWIN, VK_LWIN},
|
||||
{ IDENT_KEY_RWIN, VK_RWIN},
|
||||
|
||||
{ IDENT_KEY_LBUTTON, VK_LBUTTON},
|
||||
{ IDENT_KEY_RBUTTON, VK_RBUTTON},
|
||||
{ IDENT_KEY_MBUTTON, VK_MBUTTON},
|
||||
|
||||
{ IDENT_KEY_ENTER, VK_RETURN},
|
||||
{ IDENT_KEY_UP, VK_UP},
|
||||
{ IDENT_KEY_DOWN, VK_DOWN},
|
||||
{ IDENT_KEY_LEFT, VK_LEFT},
|
||||
{ IDENT_KEY_RIGHT, VK_RIGHT},
|
||||
{ IDENT_KEY_BACK, VK_BACK},
|
||||
{ IDENT_KEY_CAPITAL, VK_CAPITAL},
|
||||
{ IDENT_KEY_DELETE, VK_DELETE},
|
||||
{ IDENT_KEY_END, VK_END},
|
||||
{ IDENT_KEY_F1, VK_F1},
|
||||
{ IDENT_KEY_F10, VK_F10},
|
||||
{ IDENT_KEY_F11, VK_F11},
|
||||
{ IDENT_KEY_F12, VK_F12},
|
||||
{ IDENT_KEY_F2, VK_F2},
|
||||
{ IDENT_KEY_F3, VK_F3},
|
||||
{ IDENT_KEY_F4, VK_F4},
|
||||
{ IDENT_KEY_F5, VK_F5},
|
||||
{ IDENT_KEY_F6, VK_F6},
|
||||
{ IDENT_KEY_F7, VK_F7},
|
||||
{ IDENT_KEY_F8, VK_F8},
|
||||
{ IDENT_KEY_F9, VK_F9},
|
||||
{ IDENT_KEY_HELP, VK_HELP},
|
||||
{ IDENT_KEY_HOME, VK_HOME},
|
||||
{ IDENT_KEY_INSERT, VK_INSERT},
|
||||
{ IDENT_KEY_NEXT, VK_NEXT},
|
||||
{ IDENT_KEY_PAUSE, VK_PAUSE},
|
||||
{ IDENT_KEY_PRIOR, VK_PRIOR},
|
||||
{ IDENT_KEY_APPS, VK_APPS},
|
||||
{ IDENT_KEY_CAPSLOCK, VK_CAPITAL},
|
||||
{ IDENT_KEY_CANCEL, VK_CANCEL},
|
||||
{ IDENT_KEY_EXECUTE, VK_EXECUTE},
|
||||
{ IDENT_KEY_PAGEDOWN, VK_NEXT},
|
||||
{ IDENT_KEY_PAGEUP, VK_PRIOR},
|
||||
{ IDENT_KEY_PLAY, VK_PLAY},
|
||||
{ IDENT_KEY_PRINT, VK_PRINT},
|
||||
{ IDENT_KEY_PRINTSCREEN, VK_SNAPSHOT},
|
||||
{ IDENT_KEY_SNAPSHOT, VK_SNAPSHOT},
|
||||
{ IDENT_KEY_SPACE, VK_SPACE},
|
||||
{ IDENT_KEY_TAB, VK_TAB},
|
||||
{ IDENT_KEY_ESCAPE, VK_ESCAPE}
|
||||
};
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,251 @@
|
||||
#pragma once
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
enum class Privileges : int
|
||||
{
|
||||
None,
|
||||
Default,
|
||||
User,
|
||||
System,
|
||||
TrustedInstaller,
|
||||
Full
|
||||
};
|
||||
|
||||
enum class Visibility : int
|
||||
{
|
||||
None = -1,
|
||||
Hidden = 0,
|
||||
Remove = Hidden,
|
||||
Normal,
|
||||
Enabled = Normal,
|
||||
Disabled,
|
||||
Static,
|
||||
Label
|
||||
};
|
||||
|
||||
enum class Position : int
|
||||
{
|
||||
None = -5,
|
||||
Auto,
|
||||
Middle,
|
||||
Top,
|
||||
Bottom
|
||||
};
|
||||
|
||||
// Spacer
|
||||
enum class Separator : int
|
||||
{
|
||||
None,
|
||||
Top = 1,
|
||||
Bottom = 2,
|
||||
Both = Top | Bottom,
|
||||
};
|
||||
|
||||
enum class ImageImport : int
|
||||
{
|
||||
None,
|
||||
Disabled,
|
||||
Image,
|
||||
SVG,
|
||||
Command,
|
||||
Inherit,
|
||||
Parent,
|
||||
Path,
|
||||
Draw,
|
||||
SystemInherit
|
||||
};
|
||||
/*
|
||||
constexpr wchar_t *verbs[]={
|
||||
L"null",
|
||||
L"open",
|
||||
L"openas",
|
||||
L"opennew",
|
||||
L"runas",
|
||||
L"edit",
|
||||
L"explore",
|
||||
L"properties",
|
||||
L"print",
|
||||
L"printto",
|
||||
L"find",
|
||||
L"copy",
|
||||
L"cut",
|
||||
L"paste",
|
||||
L"pastelink",
|
||||
L"delete"
|
||||
}*/
|
||||
constexpr auto COMMAND_INVALID = -1;
|
||||
constexpr auto COMMAND_EXPRESSION = 0;
|
||||
constexpr auto COMMAND_PROMPT = 1;
|
||||
constexpr auto COMMAND_POWERSHELL = 2;
|
||||
constexpr auto COMMAND_PWSH = 3;
|
||||
constexpr auto COMMAND_SHELL = 4;
|
||||
constexpr auto COMMAND_EXPLORER = 5;
|
||||
|
||||
|
||||
enum class Verbs : int
|
||||
{
|
||||
Null, // Specifies that the operation is the default for the selected file type.
|
||||
Open, // Opens a file or a application
|
||||
OpenAs, // Opens dialog when no program is associated to the extension
|
||||
OpenNew, // see MSDN
|
||||
RunAs, // In Windows 7 and Vista, opens the UAC dialog andin others, open the Run as... Dialog
|
||||
Edit, // Opens the default text editor for the file.
|
||||
Explore, // Opens the Windows Explorer in the folder specified in lpDirectory.
|
||||
Properties, // Opens the properties window of the file.
|
||||
Print, // Start printing the file with the default application.
|
||||
Printto, // see MSDN
|
||||
Find, // Start a search
|
||||
Copy, // see MSDN
|
||||
Cut, // see MSDN
|
||||
Paste, // see MSDN
|
||||
PasteLink, // pastes a shortcut
|
||||
Delete, // see MSDN
|
||||
};
|
||||
|
||||
struct Application
|
||||
{
|
||||
string Path;
|
||||
string ConfigPortable;
|
||||
string Config;
|
||||
string Manager;
|
||||
string Dirctory;
|
||||
string Name;
|
||||
string Root;
|
||||
string Version;
|
||||
string FileName;
|
||||
};
|
||||
|
||||
struct this_item
|
||||
{
|
||||
int type = 0;
|
||||
int pos = -4;
|
||||
int checked = 0;
|
||||
int disabled = 0;
|
||||
bool system = false;
|
||||
bool is_uwp = false;
|
||||
uint32_t id = 0;
|
||||
uint32_t parent=0;
|
||||
uint32_t length = 0;
|
||||
const wchar_t *title{};
|
||||
const wchar_t *title_normalize{};
|
||||
const wchar_t *verb{};
|
||||
int vis = 0;
|
||||
int sep = 0;
|
||||
int level = 0;
|
||||
string clsid;
|
||||
};
|
||||
|
||||
//contains information that's global to the interpreter.
|
||||
class Context
|
||||
{
|
||||
public:
|
||||
struct CACHE* Cache = nullptr;
|
||||
|
||||
bool Runtime = true;
|
||||
bool Break = false;
|
||||
bool Continue = false;
|
||||
uint32_t invoked = 0;
|
||||
|
||||
Application *Application{};
|
||||
Shell::Selections *Selections{};
|
||||
|
||||
struct
|
||||
{
|
||||
Scope *global{};
|
||||
Scope *local{};
|
||||
Scope *runtime{};
|
||||
}variables;
|
||||
|
||||
Keyboard *Keyboard{};
|
||||
this_item *_this{};
|
||||
struct Theme *theme{};
|
||||
struct DPI *dpi{};
|
||||
|
||||
HMENU hMenu{};
|
||||
uint32_t menu_count = 0;
|
||||
|
||||
struct {
|
||||
string text;
|
||||
string icon;
|
||||
}font;
|
||||
|
||||
struct {
|
||||
uint32_t languageId = 1033;
|
||||
bool is_primary_monitor = true;
|
||||
}helper;
|
||||
|
||||
struct
|
||||
{
|
||||
HWND owner{};
|
||||
HWND active{};
|
||||
HWND focus{};
|
||||
}wnd;
|
||||
|
||||
Context() = default;
|
||||
|
||||
bool variable_exists(uint32_t id);
|
||||
class Expression* get_variable(uint32_t id, Expression *e);
|
||||
void set_variable2(uint32_t id, Expression *e, Object &&value);
|
||||
|
||||
Object &eval_object(Expression *array, Object &obj);
|
||||
bool set_variable(uint32_t id, Expression *e);
|
||||
bool to_color(const Object &obj, Color *color);
|
||||
bool eval_bool(class Expression *e);
|
||||
bool eval_number(class Expression *e, Object &obj);
|
||||
bool eval_color(class Expression *e, Color *color);
|
||||
Object Eval(class Expression *e);
|
||||
Object Eval(Expression *e, const Object &obj);
|
||||
bool Eval(Expression *e, Object &obj);
|
||||
bool Eval(Expression *e, string &value, bool trim = false);
|
||||
uint32_t Eval(Expression *e, uint32_t defualt);
|
||||
template<typename T = uint32_t>
|
||||
T eval_number(Expression *e, T default_value)
|
||||
{
|
||||
if(e)
|
||||
{
|
||||
Object obj = Eval(e).move();
|
||||
if(obj.not_default())
|
||||
return obj.to_number<T>();
|
||||
}
|
||||
return default_value;
|
||||
}
|
||||
uint32_t obj2hash(const Object &obj, auto default_value = 0) const
|
||||
{
|
||||
auto value = static_cast<uint32_t>(default_value);
|
||||
if(!obj.is_null())
|
||||
{
|
||||
if(obj.is_string())
|
||||
value = obj.to_string().trim().hash();
|
||||
else if(obj.not_default())
|
||||
value = obj;
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
uint32_t eval_hash(Expression *e, auto default_value = 0)
|
||||
{
|
||||
return obj2hash(Eval(e), default_value);
|
||||
}
|
||||
|
||||
Visibility parse_visibility(Expression *e, Visibility default_value = Visibility::Enabled);
|
||||
Position parse_position(Expression *e, Position default_value = Position::Auto);
|
||||
Position parse_pos(const Object &o, Position default_value = Position::Auto);
|
||||
Separator parse_separator(Expression *e, Separator default_value = Separator::None);
|
||||
SelectionMode parse_mode(Expression *e, SelectionMode default_value = SelectionMode::Single);
|
||||
Privileges parse_privileges(struct CommandProperty *cmd);
|
||||
Verbs parse_verbs(CommandProperty *cmd);
|
||||
int parse_window(struct CommandProperty *cmd);
|
||||
uint32_t parse_wait(struct CommandProperty *cmd);
|
||||
uint32_t parse_invoke(Expression *e);
|
||||
bool eval_tip(Expression *e, string &text, uint8_t &type, uint16_t &time);
|
||||
|
||||
bool Image(Expression *e, struct MenuItemInfo *mii, HFONT hfont, bool selected);
|
||||
|
||||
static int is_svg(Object &obj);
|
||||
// private:
|
||||
// inline static const Object empty = {};
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,194 @@
|
||||
#include <pch.h>
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
//Interpret | Eval
|
||||
//evaluate expressions
|
||||
//Evaluate an expression. Returns the result of the expression.
|
||||
|
||||
bool Expression::IsIdent() const { return Type() == ExpressionType::Identifier; }
|
||||
bool Expression::IsVariable() const
|
||||
{
|
||||
return
|
||||
Type() == ExpressionType::Variable ||
|
||||
Type() == ExpressionType::RuntimeVariable;
|
||||
}
|
||||
|
||||
bool Expression::IsAssign() const
|
||||
{
|
||||
return Type() == ExpressionType::Assign;
|
||||
}
|
||||
|
||||
bool Expression::IsLiteral() const
|
||||
{
|
||||
return Type() == ExpressionType::String ||
|
||||
Type() == ExpressionType::Number;
|
||||
}
|
||||
|
||||
LiteralExpression *Expression::Literal()
|
||||
{
|
||||
return reinterpret_cast<LiteralExpression *>(this);
|
||||
}
|
||||
|
||||
IdentExpression *Expression::ident()
|
||||
{
|
||||
return reinterpret_cast<IdentExpression *>(this);
|
||||
}
|
||||
|
||||
AssignExpression *Expression::assign()
|
||||
{
|
||||
return reinterpret_cast<AssignExpression *>(this);
|
||||
}
|
||||
|
||||
FuncExpression *Expression::identifier()
|
||||
{
|
||||
return reinterpret_cast<FuncExpression *>(this);
|
||||
}
|
||||
|
||||
Object StringExpression::Eval(Context *)
|
||||
{
|
||||
return Value;
|
||||
}
|
||||
|
||||
Object NumberExpression::Eval(Context *)
|
||||
{
|
||||
return Value;
|
||||
}
|
||||
|
||||
Object Array2Expression::Eval(Context *)
|
||||
{
|
||||
return Value;
|
||||
}
|
||||
|
||||
Object StatementExpression::Eval(Context *context)
|
||||
{
|
||||
Object _result;
|
||||
auto const &size = Body.size();
|
||||
if(size == 0)
|
||||
_result.type(PrimitiveType::String);
|
||||
else
|
||||
{
|
||||
try
|
||||
{
|
||||
if(!HasReturn)
|
||||
{
|
||||
for(auto e : Body)
|
||||
{
|
||||
try {
|
||||
context->Eval(e);
|
||||
}
|
||||
catch(...)
|
||||
{
|
||||
}
|
||||
}
|
||||
return _result;
|
||||
}
|
||||
|
||||
if(size == 1)
|
||||
_result = context->Eval(Body[0]).move();
|
||||
else
|
||||
{
|
||||
string str;
|
||||
Object r;
|
||||
for(auto e : Body)
|
||||
{
|
||||
try {
|
||||
r = context->Eval(e).move();
|
||||
if(!r.is_null())
|
||||
str.append(r.to_string());
|
||||
}
|
||||
catch(...) {}
|
||||
}
|
||||
_result = str.move();
|
||||
}
|
||||
}
|
||||
catch(...)
|
||||
{
|
||||
}
|
||||
}
|
||||
return _result.move();
|
||||
}
|
||||
|
||||
Object VariableExpression::Eval(Context *context)
|
||||
{
|
||||
if(context && context->variables.global)
|
||||
{
|
||||
if(auto variable = context->get_variable(Id, this); variable)
|
||||
{
|
||||
Object obj = context->Eval(variable).move();
|
||||
return context->eval_object(Array, obj).move();
|
||||
}
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Object AssignExpression::Eval(Context *context)
|
||||
{
|
||||
Object obj = context->Eval(Right).move();
|
||||
context->set_variable2(Id, this, obj.move());
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Object ForStatement::Eval(Context *context)
|
||||
{
|
||||
string body;
|
||||
|
||||
if(this->Init)
|
||||
{
|
||||
std::vector<string> list;
|
||||
|
||||
auto var = context->get_variable(this->Init, this)->Copy();
|
||||
int x = 0;
|
||||
|
||||
for(int i = context->Eval(var).move();
|
||||
context->Eval(Condition).to_bool(); x++)
|
||||
{
|
||||
if(x > 1000) break;
|
||||
|
||||
if(Body1)
|
||||
{
|
||||
Object o = context->Eval(Body1).move();
|
||||
list.push_back(o.to_string().move());
|
||||
}
|
||||
else for(auto e : Body2->Body)
|
||||
{
|
||||
try {
|
||||
Object o = context->Eval(e).move();
|
||||
if(o.is_number())
|
||||
{
|
||||
uint32_t id = o;
|
||||
if(id == IDENT_BREAK or context->Break)
|
||||
{
|
||||
context->Break = false;
|
||||
goto end;
|
||||
}
|
||||
else if(id == IDENT_CONTINUE or context->Continue)
|
||||
{
|
||||
context->Continue = false;
|
||||
goto skip;
|
||||
}
|
||||
}
|
||||
}
|
||||
catch(...)
|
||||
{
|
||||
}
|
||||
}
|
||||
|
||||
skip:
|
||||
Scope.set(Init, ++i);
|
||||
}
|
||||
end:
|
||||
Scope.set(Init, var);
|
||||
if(Body1)
|
||||
{
|
||||
for(auto &s : list)
|
||||
body += s;
|
||||
return body.move();
|
||||
}
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,163 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
/*
|
||||
Serialization and Unserialization
|
||||
serialize
|
||||
deserialize
|
||||
*/
|
||||
/*
|
||||
auto x = new VariableExpression("X");
|
||||
auto y = new VariableExpression("Y");
|
||||
|
||||
auto expression = new OrExpression(
|
||||
new AndExpression (new Constant(true), x),
|
||||
new AndExpression (y, new NotExpression(x))
|
||||
);
|
||||
|
||||
context.AssignX(x, true);
|
||||
context.AssignY(y, false);
|
||||
|
||||
bool result = expression->Evaluate(context);
|
||||
*/
|
||||
|
||||
class Expression abstract
|
||||
{
|
||||
protected:
|
||||
Expression() = default;
|
||||
|
||||
public:
|
||||
virtual ~Expression() = default;
|
||||
|
||||
Scope Scope;
|
||||
Expression *Parent = nullptr;
|
||||
|
||||
// Returns the type of expression.
|
||||
virtual ExpressionType Type() const = 0;
|
||||
virtual Expression *Copy() = 0;//Clone
|
||||
|
||||
// Interpreter evaluate
|
||||
// Interpret evaluate
|
||||
//Interpret | Eval
|
||||
//evaluate expressions
|
||||
//Evaluate an expression. Returns the result of the expression.
|
||||
virtual Object Eval(Context *context) = 0;
|
||||
//const Object & Interpret(context);
|
||||
|
||||
bool IsIdent() const;
|
||||
bool IsVariable() const;
|
||||
bool IsAssign() const;
|
||||
bool IsLiteral() const;
|
||||
|
||||
class LiteralExpression *Literal();
|
||||
class IdentExpression *ident();
|
||||
class AssignExpression *assign();
|
||||
class FuncExpression *identifier();
|
||||
|
||||
void set_parent(Expression *parent)
|
||||
{
|
||||
if(!Parent) Parent = parent;
|
||||
}
|
||||
};
|
||||
|
||||
struct auto_expr
|
||||
{
|
||||
Expression *_e{};
|
||||
auto_expr() = default;
|
||||
auto_expr(Expression *e) : _e{ e } {}
|
||||
auto_expr(auto_expr &&other) noexcept { *this = std::move(other); }
|
||||
virtual ~auto_expr() { delete _e; }
|
||||
|
||||
operator Expression *() { return _e; }
|
||||
operator Expression *() const { return _e; }
|
||||
|
||||
// operator const Expression *() { return _e; }
|
||||
// operator const Expression *() const { return _e; }
|
||||
|
||||
explicit operator bool() const { return _e != nullptr; }
|
||||
|
||||
Expression *get() { return _e; }
|
||||
|
||||
void reset(Expression *e = nullptr) { delete _e; _e = e; }
|
||||
Expression *release() { auto e = _e; _e = nullptr; return e; }
|
||||
auto_expr &&move() noexcept { return std::move(*this); }
|
||||
|
||||
auto_expr &operator =(Expression *rhs) noexcept
|
||||
{
|
||||
if(_e != rhs)
|
||||
{
|
||||
delete _e;
|
||||
_e = rhs;
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
auto_expr &operator =(auto_expr &&rhs) noexcept
|
||||
{
|
||||
if(_e != rhs._e)
|
||||
{
|
||||
delete _e;
|
||||
_e = rhs._e;
|
||||
rhs._e = {};
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
};
|
||||
|
||||
class NullExpression : public Expression
|
||||
{
|
||||
ExpressionType Type() const override { return ExpressionType::Null; }
|
||||
Expression *Copy() override { return new NullExpression(); }
|
||||
Object Eval(Context *) override { return nullptr; }
|
||||
};
|
||||
|
||||
|
||||
//(condition ? expressionTrue : expressionFalse)
|
||||
// (condition) ? expressionTrue : expressionFalse;
|
||||
//Conditional or Ternary Operator
|
||||
class TernaryExpression : public Expression
|
||||
{
|
||||
public:
|
||||
TernaryExpression() = default;
|
||||
TernaryExpression(Expression *condition)
|
||||
: Condition{ condition } { }
|
||||
|
||||
TernaryExpression(Expression *condition, Expression *true_stmt, Expression *false_stmt)
|
||||
: Condition{ condition }, True{ true_stmt }, False{ false_stmt }
|
||||
{
|
||||
}
|
||||
|
||||
~TernaryExpression()
|
||||
{
|
||||
delete Condition;
|
||||
delete True;
|
||||
delete False;
|
||||
}
|
||||
|
||||
ExpressionType Type() const override { return ExpressionType::Ternary; }
|
||||
Expression *Copy() override
|
||||
{
|
||||
auto ternary = new TernaryExpression(Condition->Copy());
|
||||
if(ternary->True)
|
||||
ternary->True = True->Copy();
|
||||
if(ternary->False)
|
||||
ternary->False = False->Copy();
|
||||
return ternary;
|
||||
}
|
||||
|
||||
Object Eval(Context *context) override
|
||||
{
|
||||
Object condition = context->Eval(Condition).move();
|
||||
if(condition.to_bool())
|
||||
return context->Eval(True).move();
|
||||
return context->Eval(False).move();
|
||||
}
|
||||
|
||||
Expression *Condition = nullptr;
|
||||
Expression *True = nullptr;
|
||||
Expression *False = nullptr;
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,222 @@
|
||||
#pragma once
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
enum class ExpressionType
|
||||
{
|
||||
Invalid = -1,
|
||||
None,
|
||||
Null,
|
||||
Literal,
|
||||
String,
|
||||
Number,
|
||||
Color,
|
||||
Array,
|
||||
Statement,
|
||||
BinaryOperator,
|
||||
UnaryOperator,
|
||||
Ternary, //Operator (?:)
|
||||
|
||||
Identifier,
|
||||
Function,
|
||||
Variable,
|
||||
RuntimeVariable,
|
||||
For,
|
||||
ForEach,
|
||||
Assign, //An assignment operation, such as (a = b).
|
||||
StringExt
|
||||
/*
|
||||
Constant, //A constant value.
|
||||
Add, //An addition operation, such as a + b, without overflow checking, for numeric operands.
|
||||
AddAssign, //An addition compound assignment operation, such as (a += b), without overflow checking, for numeric operands.
|
||||
And, //A bitwise or logical AND operation, such as (a & b) in C# and (a And b) in Visual Basic.
|
||||
AndAlso, //A conditional AND operation that evaluates the second operand only if the first operand evaluates to true. It corresponds to (a && b) in C#.
|
||||
AndAssign, //A bitwise or logical AND compound assignment operation, such as (a &= b) in C#
|
||||
Call, //A method call, such as in the obj.sampleMethod() expression.
|
||||
Coalesce, //A node that represents a null coalescing operation, such as(a ? ? b) in C# or If(a, b) in Visual Basic.
|
||||
Conditional, //A conditional operation, such as a > b ? a : b in C# or If(a > b, a, b) in Visual Basic.
|
||||
Divide, //A division operation, such as(a / b), for numeric operands.
|
||||
DivideAssign, //An division compound assignment operation, such as(a /= b), for numeric operands.
|
||||
Equal, //A node that represents an equality comparison, such as(a == b) in C# or (a = b) in Visual Basic.
|
||||
ExclusiveOr, //A bitwise or logical XOR operation, such as(a ^b) in C# or (a Xor b) in Visual Basic.
|
||||
ExclusiveOrAssign, //A bitwise or logical XOR compound assignment operation, such as(a ^= b) in C#.
|
||||
GreaterThan, //A "greater than" comparison, such as(a > b).
|
||||
GreaterThanOrEqual, //A "greater than or equal to" comparison, such as(a >= b).
|
||||
IsFalse, //A false condition value.
|
||||
IsTrue, //A true condition value.
|
||||
LeftShift, //A bitwise left - shift operation, such as(a << b).
|
||||
LeftShiftAssign, //A bitwise left - shift compound assignment, such as(a <<= b).
|
||||
LessThan, //A "less than" comparison, such as(a < b).
|
||||
LessThanOrEqual,//A "less than or equal to" comparison, such as(a <= b).
|
||||
Loop, //A loop, such as for or while.
|
||||
MemberAccess, //An operation that reads from a field or property, such as obj.SampleProperty.
|
||||
Modulo, //An arithmetic remainder operation, such as(a %b) in C# or (a Mod b) in Visual Basic.
|
||||
ModuloAssign, //An arithmetic remainder compound assignment operation, such as(a %= b) in C#.
|
||||
Multiply, //A multiplication operation, such as(a *b), without overflow checking, for numeric operands.
|
||||
MultiplyAssign, //A multiplication compound assignment operation, such as(a *= b), without overflow checking, for numeric operands.
|
||||
MultiplyChecked,//An multiplication operation, such as(a *b), that has overflow checking, for numeric operands.
|
||||
Negate, //An arithmetic negation operation, such as(-a).The object a should not be modified in place.
|
||||
Not, //A bitwise complement or logical negation operation.In C#, it is equivalent to(~a) for integral types and to(!a) for Boolean values.In Visual Basic, it is equivalent to(Not a).The object a should not be modified in place.
|
||||
NotEqual, //An inequality comparison, such as(a != b) in C# or (a <> b) in Visual Basic.
|
||||
OnesComplement, //A ones complement operation, such as(~a) in C#.
|
||||
Or, //A bitwise or logical OR operation, such as(a | b) in C# or (a Or b) in Visual Basic.
|
||||
OrAssign, //A bitwise or logical OR compound assignment, such as(a |= b) in C#.
|
||||
OrElse, //A short - circuiting conditional OR operation, such as(a || b) in C# or (a OrElse b) in Visual Basic.
|
||||
Power, //A mathematical operation that raises a number to a power, such as(a ^b) in Visual Basic.
|
||||
PowerAssign, //A compound assignment operation that raises a number to a power, such as(a ^= b) in Visual Basic.
|
||||
Quote, //An expression that has a constant value of type Expression.A Quote node can contain references to parameters that are defined in the context of the expression it represents.
|
||||
RightShift, //A bitwise right - shift operation, such as(a >> b).
|
||||
RightShiftAssign,//A bitwise right - shift compound assignment operation, such as(a >>= b).
|
||||
//RuntimeVariables,//A list of run - time variables.For more information, see RuntimeVariablesExpression.
|
||||
Subtract, //A subtraction operation, such as(a - b), without overflow checking, for numeric operands.
|
||||
SubtractAssign,//A subtraction compound assignment operation, such as(a -= b), without overflow checking, for numeric operands.
|
||||
UnaryPlus //A unary plus operation, such as(+a).The result of a predefined unary plus operation is the value of the operand, but user - defined implementations might have unusual results.
|
||||
*/
|
||||
};
|
||||
|
||||
|
||||
enum class OperatorType : int
|
||||
{
|
||||
None,
|
||||
Invalid = None,
|
||||
Comma,
|
||||
Equal, // =, *=, /=, %=, +=, -=, <<=, >>=, &=, ^=, |= Right-to-left
|
||||
MinusEqual,
|
||||
PlusEqual,
|
||||
|
||||
Question, // ? Ternary conditional
|
||||
LogicalOr, // || Logical or
|
||||
LogicalAnd, // && Logical and
|
||||
BitwiseOr, // | Inclusive or
|
||||
BitwiseXor, // ^ Exclusive or
|
||||
BitwiseAnd, // & Bitwise and
|
||||
|
||||
// Equality
|
||||
EqualEqual, // ==
|
||||
NotEqual, // !=
|
||||
|
||||
// Comparison Operations
|
||||
GreaterThan,
|
||||
GreaterThanOrEqual,
|
||||
LessThan,
|
||||
LessThanOrEqual,
|
||||
|
||||
// Shift Operations
|
||||
BitwiseLeftShift,
|
||||
BitwiseRightShift,
|
||||
|
||||
// Additive
|
||||
Plus, // +
|
||||
Minus, // -
|
||||
|
||||
PlusPlus,
|
||||
MinusMinus,
|
||||
|
||||
// Multiplicative
|
||||
Multiply,
|
||||
Divide,
|
||||
Modulo,
|
||||
//
|
||||
// Right-to-left
|
||||
//
|
||||
BitwiseNot, // ~
|
||||
LogicalNot, // !
|
||||
|
||||
// Unary Operations
|
||||
UnaryPlus, // +a
|
||||
UnaryMinus, // -a
|
||||
UnaryNot, // !a
|
||||
UnaryNegation, // ~a
|
||||
|
||||
// Prefix increment and decrement
|
||||
PrefixInc, // --a
|
||||
PrefixDec, // ++a
|
||||
|
||||
// Left-to-right
|
||||
|
||||
//Suffix / postfix increment and decrement a++,a--
|
||||
PostfixInc, // a--
|
||||
PostfixDec, // a++
|
||||
//a() Function call
|
||||
//a[] Subscript
|
||||
//. Member access
|
||||
MemberAccess // ., a[], a()
|
||||
};
|
||||
|
||||
// PrecedenceLevels - These are precedences for the binary/ternary
|
||||
// operators in the C99 grammar. These have been named to relate
|
||||
// with the C99 grammar productions. Low precedences numbers bind
|
||||
// more weakly than high numbers.
|
||||
/*enum class PrecedenceLevels
|
||||
{
|
||||
Unknown = 0, // Not binary operator.
|
||||
Comma = 1, // ,
|
||||
Assignment = 2, // =, *=, /=, %=, +=, -=, <<=, >>=, &=, ^=, |= Right-to-left
|
||||
Conditional = 3, // ? Right-to-left
|
||||
LogicalOr = 4, // ||
|
||||
LogicalAnd = 5, // &&
|
||||
BitwiseOr = 6, // |
|
||||
BitwiseXor = 7, // ^
|
||||
BitwiseAnd = 8, // &
|
||||
Equality = 9, // ==, !=
|
||||
Relational = 10, // >=, <=, >, < Comparison
|
||||
Shift = 12, // <<, >>
|
||||
Additive = 13, // -, +
|
||||
Multiplicative = 14, // *, /, %
|
||||
Unaray = 15, // !a, ~a, -a, +a Right-to-left
|
||||
MemberAccess = 16 // ., a[], a()
|
||||
};*/
|
||||
|
||||
/*
|
||||
static bool IsRightAssociative(SyntaxKind op)
|
||||
{
|
||||
switch (op)
|
||||
{
|
||||
case SyntaxKind.SimpleAssignmentExpression:
|
||||
case SyntaxKind.AddAssignmentExpression:
|
||||
case SyntaxKind.SubtractAssignmentExpression:
|
||||
case SyntaxKind.MultiplyAssignmentExpression:
|
||||
case SyntaxKind.DivideAssignmentExpression:
|
||||
case SyntaxKind.ModuloAssignmentExpression:
|
||||
case SyntaxKind.AndAssignmentExpression:
|
||||
case SyntaxKind.ExclusiveOrAssignmentExpression:
|
||||
case SyntaxKind.OrAssignmentExpression:
|
||||
case SyntaxKind.LeftShiftAssignmentExpression:
|
||||
case SyntaxKind.RightShiftAssignmentExpression:
|
||||
case SyntaxKind.CoalesceAssignmentExpression:
|
||||
case SyntaxKind.CoalesceExpression:
|
||||
return true;
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
}
|
||||
enum Precedence : uint
|
||||
{
|
||||
Expression = 0, // Loosest possible precedence, used to accept all expressions
|
||||
Assignment = Expression,
|
||||
Lambda = Assignment, // "The => operator has the same precedence as assignment (=) and is right-associative."
|
||||
Conditional,
|
||||
Coalescing,
|
||||
ConditionalOr,
|
||||
ConditionalAnd,
|
||||
LogicalOr,
|
||||
LogicalXor,
|
||||
LogicalAnd,
|
||||
Equality,
|
||||
Relational,
|
||||
Shift,
|
||||
Additive,
|
||||
Mutiplicative,
|
||||
Switch,
|
||||
Range,
|
||||
Unary,
|
||||
Cast,
|
||||
PointerIndirection,
|
||||
AddressOf,
|
||||
Primary,
|
||||
}
|
||||
|
||||
*/
|
||||
}
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,285 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
class IdentExpression abstract: public Expression
|
||||
{
|
||||
public:
|
||||
Ident Id{};
|
||||
bool Brackets = false;
|
||||
Expression *Array = nullptr;
|
||||
|
||||
public:
|
||||
IdentExpression(const Ident &ident) : Id{ ident }
|
||||
{
|
||||
}
|
||||
|
||||
virtual ~IdentExpression() = default;
|
||||
};
|
||||
|
||||
class VariableExpression final : public IdentExpression
|
||||
{
|
||||
public:
|
||||
|
||||
VariableExpression(const Ident &ident, Expression *parent = nullptr)
|
||||
: IdentExpression(ident)
|
||||
{
|
||||
Parent = parent;
|
||||
}
|
||||
|
||||
~VariableExpression() = default;
|
||||
|
||||
ExpressionType Type() const
|
||||
{
|
||||
return ExpressionType::Variable;
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
auto e = new VariableExpression(Id, Parent);
|
||||
e->Array = Array ? Array->Copy() : nullptr;
|
||||
e->Brackets = Brackets;
|
||||
return e;
|
||||
}
|
||||
|
||||
Object Eval(Context *context) override;
|
||||
};
|
||||
|
||||
class AssignExpression final : public IdentExpression
|
||||
{
|
||||
public:
|
||||
Expression *Right = nullptr;
|
||||
|
||||
public:
|
||||
|
||||
AssignExpression(const Ident &ident, Expression *right, Expression *parent = nullptr)
|
||||
: IdentExpression(ident), Right{ right }
|
||||
{
|
||||
Parent = parent;
|
||||
}
|
||||
|
||||
~AssignExpression() { delete Right; }
|
||||
|
||||
ExpressionType Type() const
|
||||
{
|
||||
return ExpressionType::Assign;
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
return new AssignExpression(Id, Right->Copy(), Parent);
|
||||
}
|
||||
|
||||
Object Eval(Context *context) override;
|
||||
};
|
||||
|
||||
class ForStatement final : public Expression
|
||||
{
|
||||
public:
|
||||
ForStatement(Expression *parent = nullptr)
|
||||
{
|
||||
Parent = parent;
|
||||
}
|
||||
|
||||
~ForStatement()
|
||||
{
|
||||
delete Condition;
|
||||
delete Iterator;
|
||||
delete Body1;
|
||||
delete Body2;
|
||||
}
|
||||
|
||||
ExpressionType Type() const override { return ExpressionType::For; }
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
auto stmt = new ForStatement();
|
||||
|
||||
stmt->Init = Init;
|
||||
|
||||
if(Condition)
|
||||
stmt->Condition = Condition->Copy();
|
||||
|
||||
if(Iterator)
|
||||
stmt->Iterator = Iterator->Copy();
|
||||
|
||||
if(Body1)
|
||||
stmt->Body1 = (StatementExpression *)Body1->Copy();
|
||||
|
||||
if(Body2)
|
||||
stmt->Body2 = (StatementExpression *)Body2->Copy();
|
||||
|
||||
return stmt;
|
||||
}
|
||||
|
||||
Object Eval(Context *context) override;
|
||||
|
||||
uint32_t Init = 0;
|
||||
Expression *Condition = nullptr;
|
||||
Expression *Iterator = nullptr;
|
||||
Expression *Body1 = nullptr;
|
||||
StatementExpression *Body2 = nullptr;
|
||||
};
|
||||
|
||||
class FuncExpression final : public IdentExpression
|
||||
{
|
||||
Object _result;
|
||||
Context *context = nullptr;
|
||||
struct CACHE* cache = nullptr;
|
||||
|
||||
bool eval = false;
|
||||
|
||||
public:
|
||||
bool ischild = false;
|
||||
bool extented = false;
|
||||
|
||||
std::vector<Expression *> Arguments{ };
|
||||
Shell::Scope Variables;
|
||||
|
||||
FuncExpression *Child = nullptr;
|
||||
|
||||
public:
|
||||
|
||||
FuncExpression(const Ident &ident, Expression *parent = nullptr)
|
||||
: IdentExpression(ident)
|
||||
{
|
||||
Parent = parent;
|
||||
}
|
||||
|
||||
~FuncExpression()
|
||||
{
|
||||
for(auto e : Arguments) delete e;
|
||||
|
||||
delete Array;
|
||||
delete Child;
|
||||
}
|
||||
|
||||
ExpressionType Type() const override
|
||||
{
|
||||
return ExpressionType::Identifier;
|
||||
}
|
||||
|
||||
void SetChild(Expression* child)
|
||||
{
|
||||
if(child)
|
||||
{
|
||||
Child = (FuncExpression *)child;
|
||||
Child->Parent = this;
|
||||
Child->ischild = true;
|
||||
}
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
auto func = new FuncExpression(Id, Parent);
|
||||
for(auto e : Arguments)
|
||||
func->Arguments.push_back(e->Copy());
|
||||
|
||||
if(Child)
|
||||
{
|
||||
func->Child = (FuncExpression *)Child->Copy();
|
||||
func->Child->ischild = true;
|
||||
func->Child->Parent = func;
|
||||
func->Array = Array->Copy();
|
||||
}
|
||||
|
||||
return func;
|
||||
}
|
||||
|
||||
Object Eval(Context *context) override;
|
||||
|
||||
// Add argument
|
||||
void push_back(Expression *e)
|
||||
{
|
||||
e->Parent = this;
|
||||
Arguments.push_back(e);
|
||||
}
|
||||
|
||||
void push_front(Expression *e)
|
||||
{
|
||||
e->Parent = this;
|
||||
if(Arguments.size() == 0)
|
||||
Arguments.push_back(e);
|
||||
else
|
||||
Arguments.insert(Arguments.begin(), e);
|
||||
}
|
||||
|
||||
Object operator()(size_t arg);
|
||||
Expression *operator[](size_t arg);
|
||||
|
||||
// Evaluate arguments
|
||||
Object eval_arg(size_t arg);
|
||||
|
||||
template<typename T>
|
||||
T eval_arg(size_t arg, T const &default_value);
|
||||
|
||||
private:
|
||||
void eval_sel();
|
||||
void eval_path();
|
||||
void eval_io();
|
||||
void eval_user();
|
||||
void eval_sys();
|
||||
void eval_app();
|
||||
void eval_str();
|
||||
void eval_for();
|
||||
void eval_foreach();
|
||||
void eval_reg();
|
||||
void eval_msg();
|
||||
void eval_icon();
|
||||
|
||||
Object eval_key();
|
||||
Object eval_color();
|
||||
bool eval_var(Object &);
|
||||
bool eval_var(uint32_t id, Object &obj);
|
||||
};
|
||||
|
||||
/*class IfExpression : public Expression
|
||||
{
|
||||
Context *context = nullptr;
|
||||
Object _result;
|
||||
|
||||
private:
|
||||
IfExpression() = default;
|
||||
|
||||
public:
|
||||
Expression *Expr = nullptr;
|
||||
Expression *Stmt = nullptr;
|
||||
Expression *ElseStmt = nullptr;
|
||||
|
||||
public:
|
||||
|
||||
IfExpression()
|
||||
{
|
||||
}
|
||||
|
||||
~IfExpression()
|
||||
{
|
||||
delete Expr;
|
||||
delete Stmt;
|
||||
delete ElseStmt;
|
||||
}
|
||||
|
||||
ExpressionType Type() const override
|
||||
{
|
||||
return ExpressionType::Identifier;
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
auto ifexpr = new IfExpression();
|
||||
if(Expr)
|
||||
ifexpr->Expr = Expr->Copy();
|
||||
if(Stmt)
|
||||
ifexpr->Stmt = Stmt->Copy();
|
||||
if(ElseStmt)
|
||||
ifexpr->ElseStmt = ElseStmt->Copy();
|
||||
return ifexpr;
|
||||
}
|
||||
|
||||
Object Eval(Context *context) override;
|
||||
private:
|
||||
};*/
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,112 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
class LiteralExpression : public Expression
|
||||
{
|
||||
public:
|
||||
LiteralExpression(const Object &value) : Value{ value } {}
|
||||
LiteralExpression(Object &&value) : Value{ std::move(value) } {}
|
||||
virtual ~LiteralExpression() = default;
|
||||
|
||||
public:
|
||||
Object Value;
|
||||
};
|
||||
|
||||
class StringExpression final : public LiteralExpression
|
||||
{
|
||||
public:
|
||||
StringExpression(const Object &value) : LiteralExpression(value) {}
|
||||
StringExpression(const string &value) : LiteralExpression(value) {}
|
||||
StringExpression(string &&value) : LiteralExpression(value.move()){}
|
||||
StringExpression(std::wstring const &value) : LiteralExpression(value) {}
|
||||
//StringExpression(std::wstring &&value) : LiteralExpression(std::move(value)) {}
|
||||
StringExpression(const wchar_t *value) : LiteralExpression(value) {}
|
||||
StringExpression(wchar_t value) : LiteralExpression(value) {}
|
||||
StringExpression(char value) : LiteralExpression(value) {}
|
||||
|
||||
ExpressionType Type() const override
|
||||
{
|
||||
return ExpressionType::String;
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
return new StringExpression(Value);
|
||||
}
|
||||
|
||||
Object Eval(Context *context) override;
|
||||
};
|
||||
|
||||
class NumberExpression final : public LiteralExpression
|
||||
{
|
||||
public:
|
||||
template<typename T>
|
||||
NumberExpression(T value)
|
||||
: LiteralExpression(value){ }
|
||||
|
||||
template<typename T>
|
||||
NumberExpression(T value, PrimitiveType inner)
|
||||
: LiteralExpression(value)
|
||||
{
|
||||
Value.Value.Inner = inner;
|
||||
}
|
||||
|
||||
ExpressionType Type() const override
|
||||
{
|
||||
return ExpressionType::Number;
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
return new NumberExpression(Value);
|
||||
}
|
||||
|
||||
Object Eval(Context *context) override;
|
||||
};
|
||||
|
||||
class Array2Expression final : public LiteralExpression
|
||||
{
|
||||
public:
|
||||
Array2Expression(const Object &value) : LiteralExpression(value) {}
|
||||
Array2Expression(Object &&value) : LiteralExpression(value.move()) {}
|
||||
|
||||
ExpressionType Type() const override
|
||||
{
|
||||
return ExpressionType::Literal;
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
return new NumberExpression(Value);
|
||||
}
|
||||
|
||||
Object Eval(Context *context) override;
|
||||
};
|
||||
|
||||
/*class ColorExpression final : public LiteralExpression
|
||||
{
|
||||
public:
|
||||
template<typename T>
|
||||
ColorExpression(T value)
|
||||
: LiteralExpression(value)
|
||||
{
|
||||
}
|
||||
|
||||
ExpressionType Type() const override
|
||||
{
|
||||
return ExpressionType::Color;
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
return new NumberExpression(Value);
|
||||
}
|
||||
|
||||
//virtual const Object &Eval() override;
|
||||
Object Eval(Context *context) override;
|
||||
};*/
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,217 @@
|
||||
#include <pch.h>
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
Object UnaryExpression::Eval(Context *context)
|
||||
{
|
||||
Object _result, operand = context->Eval(Operand).move();
|
||||
if(!operand.is_null())
|
||||
{
|
||||
if(operand.is_string())
|
||||
{
|
||||
if(Operator == OperatorType::UnaryNot)
|
||||
_result = operand.Value.String.empty();
|
||||
else
|
||||
Logger::Debug(L"Invalid unary operator type.");
|
||||
}
|
||||
else switch(Operator)
|
||||
{
|
||||
case OperatorType::UnaryPlus:
|
||||
_result = +(operand.Value.Number);
|
||||
break;
|
||||
case OperatorType::UnaryMinus:
|
||||
_result = -(operand.Value.Number);
|
||||
break;
|
||||
case OperatorType::UnaryNegation:
|
||||
_result = ~operand.to_number<intptr_t>();
|
||||
break;
|
||||
case OperatorType::UnaryNot:
|
||||
_result = !operand.to_number<double>();
|
||||
break;
|
||||
default:
|
||||
Logger::Debug(L"Invalid unary operator type.");
|
||||
//throw Exception("Invalid unary operator type.");
|
||||
break;
|
||||
}
|
||||
}
|
||||
return _result.move();
|
||||
}
|
||||
|
||||
Object BinaryExpression::Eval(Context *context)
|
||||
{
|
||||
Object _result;
|
||||
|
||||
try
|
||||
{
|
||||
Object lhs = context->Eval(Left).move();
|
||||
|
||||
if(this->Operator == OperatorType::LogicalAnd)
|
||||
{
|
||||
if(!lhs.to_bool())
|
||||
{
|
||||
_result = false;
|
||||
return _result.move();
|
||||
}
|
||||
}
|
||||
else if(this->Operator == OperatorType::LogicalOr)
|
||||
{
|
||||
if(lhs.to_bool())
|
||||
{
|
||||
_result = true;
|
||||
return _result.move();
|
||||
}
|
||||
}
|
||||
|
||||
Object rhs = context->Eval(Right).move();
|
||||
|
||||
if(!lhs.is_number() || !rhs.is_number())
|
||||
{
|
||||
switch(this->Operator)
|
||||
{
|
||||
case OperatorType::Plus:
|
||||
_result = (lhs.to_string() + rhs.to_string()).move();
|
||||
break;
|
||||
case OperatorType::EqualEqual:
|
||||
_result = lhs.to_string().equals(rhs.to_string());
|
||||
break;
|
||||
case OperatorType::NotEqual:
|
||||
_result = !lhs.to_string().equals(rhs.to_string());
|
||||
break;
|
||||
case OperatorType::LogicalOr:
|
||||
if(lhs.is_number())
|
||||
_result = lhs.to_number<size_t>() || rhs.to_string().length();
|
||||
else if(rhs.is_number())
|
||||
_result = lhs.to_string().length() || rhs.to_number<size_t>();
|
||||
else
|
||||
_result = lhs.to_string().length() || rhs.to_string().length();
|
||||
break;
|
||||
case OperatorType::LogicalAnd:
|
||||
if(lhs.is_number())
|
||||
_result = lhs.to_number<size_t>() && rhs.to_string().length();
|
||||
else if(rhs.is_number())
|
||||
_result = lhs.to_string().length() && rhs.to_number<size_t>();
|
||||
else
|
||||
_result = lhs.to_string().length() && rhs.to_string().length();
|
||||
break;
|
||||
case OperatorType::GreaterThan:
|
||||
if(lhs.is_number())
|
||||
_result = lhs.to_number<size_t>() > rhs.to_string().length();
|
||||
else if(rhs.is_number())
|
||||
_result = lhs.to_string().length() > rhs.to_number<size_t>();
|
||||
else
|
||||
_result = lhs.to_string().length() > rhs.to_string().length();
|
||||
break;
|
||||
case OperatorType::LessThan:
|
||||
if(lhs.is_number())
|
||||
_result = lhs.to_number<size_t>() < rhs.to_string().length();
|
||||
else if(rhs.is_number())
|
||||
_result = lhs.to_string().length() < rhs.to_number<size_t>();
|
||||
else
|
||||
_result = lhs.to_string().length() < rhs.to_string().length();
|
||||
break;
|
||||
case OperatorType::GreaterThanOrEqual:
|
||||
if(lhs.is_number())
|
||||
_result = lhs.to_number<size_t>() >= rhs.to_string().length();
|
||||
else if(rhs.is_number())
|
||||
_result = lhs.to_string().length() >= rhs.to_number<size_t>();
|
||||
else
|
||||
_result = lhs.to_string().length() >= rhs.to_string().length();
|
||||
break;
|
||||
case OperatorType::LessThanOrEqual:
|
||||
if(lhs.is_number())
|
||||
_result = lhs.to_number<size_t>() <= rhs.to_string().length();
|
||||
else if(rhs.is_number())
|
||||
_result = lhs.to_string().length() <= rhs.to_number<size_t>();
|
||||
else
|
||||
_result = lhs.to_string().length() <= rhs.to_string().length();
|
||||
break;
|
||||
default:
|
||||
Logger::Debug(L"Invalid binary operator type.");
|
||||
// throw Exception("Invalid binary operator type.");
|
||||
break;
|
||||
}
|
||||
}
|
||||
else switch(this->Operator)
|
||||
{
|
||||
// Binary Arithmetic Operations
|
||||
case OperatorType::Plus:
|
||||
_result = lhs.to_number<double>() + rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::Minus:
|
||||
_result = lhs.to_number<double>() - rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::Multiply:
|
||||
_result = lhs.to_number<double>() * rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::Divide:
|
||||
_result = lhs.to_number<double>() / rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::Modulo:
|
||||
_result = lhs.to_number<intptr_t>() % rhs.to_number<intptr_t>();
|
||||
break;
|
||||
// Logical Operations
|
||||
case OperatorType::EqualEqual:
|
||||
_result = lhs.to_number<double>() == rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::NotEqual:
|
||||
_result = lhs.to_number<double>() != rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::GreaterThan:
|
||||
_result = lhs.to_number<double>() > rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::LessThan:
|
||||
_result = lhs.to_number<double>() < rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::GreaterThanOrEqual:
|
||||
_result = lhs.to_number<double>() >= rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::LessThanOrEqual:
|
||||
_result = lhs.to_number<double>() <= rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::LogicalOr:
|
||||
_result = lhs.to_number<double>() || rhs.to_number<double>();
|
||||
break;
|
||||
case OperatorType::LogicalAnd:
|
||||
_result = lhs.to_number<double>() && rhs.to_number<double>();
|
||||
break;
|
||||
// Bitwise Operations
|
||||
case OperatorType::BitwiseXor:
|
||||
_result = lhs.to_number<intptr_t>() ^ rhs.to_number<intptr_t>();
|
||||
break;
|
||||
case OperatorType::BitwiseAnd:
|
||||
_result = lhs.to_number<intptr_t>() & rhs.to_number<intptr_t>();
|
||||
break;
|
||||
case OperatorType::BitwiseNot:
|
||||
{
|
||||
auto r = lhs.to_number<intptr_t>();
|
||||
r &= ~rhs.to_number<intptr_t>();
|
||||
_result = r;
|
||||
break;
|
||||
}
|
||||
case OperatorType::BitwiseOr:
|
||||
_result = lhs.to_number<intptr_t>() | rhs.to_number<intptr_t>();
|
||||
break;
|
||||
case OperatorType::BitwiseLeftShift:
|
||||
_result = lhs.to_number<intptr_t>() << rhs.to_number<intptr_t>();
|
||||
break;
|
||||
case OperatorType::BitwiseRightShift:
|
||||
_result = lhs.to_number<intptr_t>() >> rhs.to_number<intptr_t>();
|
||||
break;
|
||||
default:
|
||||
Logger::Debug(L"Invalid binary operator type.");
|
||||
// throw Exception("Invalid binary operator type.");
|
||||
break;
|
||||
}
|
||||
}
|
||||
catch(...)
|
||||
{
|
||||
#ifdef _DEBUG
|
||||
Logger::Exception(__func__);
|
||||
#endif
|
||||
}
|
||||
return _result.move();
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,86 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
class OperatorExpression abstract : public Expression
|
||||
{
|
||||
public:
|
||||
OperatorType Operator;
|
||||
|
||||
public:
|
||||
OperatorExpression(OperatorType operatorType)
|
||||
: Operator{ operatorType }
|
||||
{
|
||||
}
|
||||
|
||||
virtual ~OperatorExpression() = default;
|
||||
};
|
||||
|
||||
class UnaryExpression final : public OperatorExpression
|
||||
{
|
||||
public:
|
||||
Expression *Operand = nullptr;
|
||||
|
||||
public:
|
||||
UnaryExpression(OperatorType operatorType, Expression *operand =nullptr, Expression *parent = nullptr) :
|
||||
OperatorExpression(operatorType), Operand{ operand }
|
||||
{
|
||||
Parent = parent;
|
||||
}
|
||||
|
||||
~UnaryExpression()
|
||||
{
|
||||
delete Operand;
|
||||
}
|
||||
|
||||
ExpressionType Type() const override
|
||||
{
|
||||
return ExpressionType::UnaryOperator;
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
return new UnaryExpression(Operator, Operand->Copy());
|
||||
}
|
||||
|
||||
Object Eval(Context *context) override;
|
||||
};
|
||||
|
||||
class BinaryExpression final : public OperatorExpression
|
||||
{
|
||||
public:
|
||||
Expression *Left = nullptr;
|
||||
Expression *Right = nullptr;
|
||||
|
||||
public:
|
||||
BinaryExpression(OperatorType op, Expression *lhs = nullptr, Expression *rhs = nullptr, Expression *parent = nullptr)
|
||||
: OperatorExpression(op), Left{ lhs }, Right{ rhs }
|
||||
{
|
||||
if(Left) Left->Parent = this;
|
||||
if(Right) Right->Parent = this;
|
||||
Parent = parent;
|
||||
}
|
||||
|
||||
~BinaryExpression()
|
||||
{
|
||||
delete Left;
|
||||
delete Right;
|
||||
}
|
||||
|
||||
ExpressionType Type() const override
|
||||
{
|
||||
return ExpressionType::BinaryOperator;
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
return new BinaryExpression(Operator, Left->Copy(), Right->Copy());
|
||||
}
|
||||
|
||||
//virtual const Object &Eval() override;
|
||||
Object Eval(Context *context) override;
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,149 @@
|
||||
#include <pch.h>
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
void Scope::clear(bool destroy)
|
||||
{
|
||||
if(destroy)
|
||||
{
|
||||
for(auto &it : _dispatch) delete it.second;
|
||||
}
|
||||
_dispatch.clear();
|
||||
}
|
||||
|
||||
auto Scope::find(uint32_t id)
|
||||
{
|
||||
return _dispatch.find(id);
|
||||
}
|
||||
|
||||
Expression *Scope::to_expr(const Object &obj)
|
||||
{
|
||||
if(obj.is_string())
|
||||
return new StringExpression(obj.to_string());
|
||||
else if(obj.is_color())
|
||||
return new NumberExpression(obj.to_number(), PrimitiveType::Color);
|
||||
else if(obj.is_number())
|
||||
return new NumberExpression(obj.to_number<double>());
|
||||
else if(obj.is_array(true))
|
||||
{
|
||||
std::unique_ptr<ArrayExpression> array(new ArrayExpression);
|
||||
auto ptr = obj.get_pointer();
|
||||
uint32_t argc = ptr[0];
|
||||
for(auto i = 0u; i < argc; i++)
|
||||
array->push_back(to_expr(ptr[i + 1]));
|
||||
return array.release();
|
||||
}
|
||||
return new NullExpression;
|
||||
}
|
||||
|
||||
void Scope::set(uint32_t id, Expression *e)
|
||||
{
|
||||
auto pair = _dispatch.find(id);
|
||||
if(pair != _dispatch.end())
|
||||
{
|
||||
if(e == nullptr)
|
||||
{
|
||||
delete std::exchange(pair->second, nullptr);
|
||||
_dispatch.erase(pair);
|
||||
}
|
||||
else if(pair->second != e)
|
||||
{
|
||||
delete pair->second;
|
||||
pair->second = e;
|
||||
}
|
||||
}
|
||||
else if(e != nullptr)
|
||||
{
|
||||
_dispatch[id] = e;
|
||||
}
|
||||
}
|
||||
|
||||
void Scope::set(uint32_t id, Object &value)
|
||||
{
|
||||
auto pair = _dispatch.find(id);
|
||||
if(pair != _dispatch.end())
|
||||
delete pair->second;
|
||||
_dispatch.insert_or_assign(id, to_expr(value));
|
||||
}
|
||||
|
||||
void Scope::set(uint32_t id, double value)
|
||||
{
|
||||
auto pair = _dispatch.find(id);
|
||||
if(pair == _dispatch.end())
|
||||
_dispatch[id] = new NumberExpression(value);
|
||||
else if(pair->second->Type() == ExpressionType::Number)
|
||||
{
|
||||
auto e = (NumberExpression *)pair->second;
|
||||
e->Value = value;
|
||||
}
|
||||
else
|
||||
{
|
||||
delete pair->second;
|
||||
pair->second = new NumberExpression(value);
|
||||
}
|
||||
}
|
||||
|
||||
void Scope::set(uint32_t id, const string &value)
|
||||
{
|
||||
auto pair = _dispatch.find(id);
|
||||
if(pair == _dispatch.end())
|
||||
_dispatch[id] = new StringExpression(value);
|
||||
else if(pair->second->Type() == ExpressionType::String)
|
||||
{
|
||||
auto e = (StringExpression *)pair->second;
|
||||
e->Value = value;
|
||||
}
|
||||
else
|
||||
{
|
||||
delete pair->second;
|
||||
pair->second = new StringExpression(value);
|
||||
}
|
||||
}
|
||||
|
||||
void Scope::erase(uint32_t id)
|
||||
{
|
||||
auto pair = _dispatch.find(id);
|
||||
if(pair != _dispatch.end())
|
||||
{
|
||||
delete std::exchange(pair->second, nullptr);
|
||||
_dispatch.erase(pair);
|
||||
}
|
||||
}
|
||||
|
||||
bool Scope::exists(uint32_t id, bool hierarchy)
|
||||
{
|
||||
bool result = _dispatch.find(id) != _dispatch.end();
|
||||
if(!hierarchy || result)
|
||||
return result;
|
||||
|
||||
auto parent = Parent;
|
||||
while(parent)
|
||||
{
|
||||
result = parent->exists(id, hierarchy);
|
||||
if(result) break;
|
||||
parent = parent->Parent;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
//bool Scope::exists(uint32_t id) { return _dispatch.find(id) != _dispatch.end(); }
|
||||
size_t Scope::size() const { return _dispatch.size(); }
|
||||
|
||||
Expression *Scope::at(uint32_t id)
|
||||
{
|
||||
if(!_dispatch.empty())
|
||||
{
|
||||
if(auto v = _dispatch.find(id); v != _dispatch.end())
|
||||
return v->second;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Expression *Scope::operator [](uint32_t id)
|
||||
{
|
||||
return at(id);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,40 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
class Scope
|
||||
{
|
||||
//using pair = std::pair<uint32_t, Expression *>;
|
||||
std::unordered_map<uint32_t, class Expression *> _dispatch;
|
||||
|
||||
public:
|
||||
Scope *Parent = nullptr;
|
||||
|
||||
Scope() = default;
|
||||
~Scope() { clear(true); }
|
||||
|
||||
void clear(bool destroy);
|
||||
auto find(uint32_t id);
|
||||
void set(uint32_t id, Expression *e);
|
||||
void set(uint32_t id, Object &value);
|
||||
void set(uint32_t id, double value);
|
||||
void set(uint32_t id, const string &value);
|
||||
void erase(uint32_t id);
|
||||
bool exists(uint32_t id, bool hierarchy = false);
|
||||
size_t size() const;
|
||||
Expression *at(uint32_t id);
|
||||
Expression *operator [](uint32_t id);
|
||||
|
||||
Expression *to_expr(const Object &obj);
|
||||
};
|
||||
|
||||
struct tagVariables
|
||||
{
|
||||
Scope *global = nullptr;
|
||||
Scope *local = nullptr;
|
||||
Scope *runtime = nullptr;
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,68 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
class StatementExpression : public Expression
|
||||
{
|
||||
public:
|
||||
std::vector<Expression *> Body;
|
||||
bool HasReturn = false;
|
||||
|
||||
public:
|
||||
StatementExpression(Expression *parent = nullptr, bool has_return = false)
|
||||
{
|
||||
Parent = parent;
|
||||
HasReturn = has_return;
|
||||
}
|
||||
|
||||
virtual ~StatementExpression() { for(auto e : Body) delete e; }
|
||||
|
||||
ExpressionType Type() const override
|
||||
{
|
||||
return ExpressionType::Statement;
|
||||
}
|
||||
|
||||
Expression *Copy() override
|
||||
{
|
||||
auto stmt = new StatementExpression(Parent);
|
||||
for(auto e : Body) stmt->push_back(e->Copy());
|
||||
return stmt;
|
||||
}
|
||||
|
||||
virtual Object Eval(Context *context) override;
|
||||
|
||||
bool size() const { return Body.size(); }
|
||||
bool empty() const { return Body.empty(); }
|
||||
|
||||
void push_back(Expression *e)
|
||||
{
|
||||
if(e)
|
||||
{
|
||||
e->Parent = this;
|
||||
Body.push_back(e);
|
||||
}
|
||||
}
|
||||
|
||||
void push_back(std::unique_ptr<Expression> &&e)
|
||||
{
|
||||
if(e)
|
||||
{
|
||||
e->Parent = this;
|
||||
Body.push_back(e.release());
|
||||
}
|
||||
}
|
||||
|
||||
void push_back(const string &value)
|
||||
{
|
||||
if(!value.empty()) push_back(new StringExpression(value));
|
||||
}
|
||||
|
||||
void push_back(string &&value)
|
||||
{
|
||||
if(!value.empty()) push_back(new StringExpression(value.move()));
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,113 @@
|
||||
#pragma once
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
/*class Variable
|
||||
{
|
||||
public:
|
||||
uint32_t Id = 0;
|
||||
Expression *Value = nullptr;
|
||||
std::vector<Variable> Items;
|
||||
|
||||
Variable() {}
|
||||
Variable(Variable &&other) noexcept { this->operator=( std::move(other)); }
|
||||
|
||||
Variable(uint32_t id) : Id(id) {}
|
||||
Variable(uint32_t id, Expression *e) : Id(id), Value(e) {}
|
||||
~Variable() { clear(); }
|
||||
|
||||
Variable(Variable const &) = delete; //default;
|
||||
Variable &operator=(Variable const &rhs) = delete;
|
||||
|
||||
Variable &operator=(Variable &&rhs) noexcept
|
||||
{
|
||||
if(this != &rhs)
|
||||
{
|
||||
clear();
|
||||
Id = rhs.Id;
|
||||
Value = rhs.Value;
|
||||
Items = std::move(rhs.Items);
|
||||
// clear old item
|
||||
rhs.Id = 0;
|
||||
rhs.Value = nullptr;
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
Variable *find(uint32_t id)
|
||||
{
|
||||
for(auto &item : Items)
|
||||
if(id == item.Id)
|
||||
return &item;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void add(uint32_t id, Expression *value)
|
||||
{
|
||||
if(auto item = find(id))
|
||||
{
|
||||
delete item->Value;
|
||||
item->Value = value;
|
||||
}
|
||||
else
|
||||
{
|
||||
Items.emplace_back(id, value);
|
||||
}
|
||||
}
|
||||
|
||||
void add(Variable &&item)
|
||||
{
|
||||
if(auto def = find(item.Id))
|
||||
{
|
||||
for(auto &x : item.Items)
|
||||
def->add(std::move(x));
|
||||
|
||||
delete def->Value;
|
||||
def->Value = item.Value;
|
||||
item.Value = nullptr;
|
||||
}
|
||||
else
|
||||
{
|
||||
Items.push_back(std::move(item));
|
||||
}
|
||||
}
|
||||
|
||||
Expression *at(uint32_t id) const
|
||||
{
|
||||
for(auto &d : Items)
|
||||
if(id == d.Id) return d.Value;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Variable *get(const Ident &id)
|
||||
{
|
||||
Variable *def = nullptr;
|
||||
for(uint32_t i = 0; i < id.length(); i++)
|
||||
{
|
||||
def = def->find(id[i]);
|
||||
if(!def) break;
|
||||
}
|
||||
return def;
|
||||
}
|
||||
|
||||
Variable &&move() noexcept { return std::move(*this); }
|
||||
|
||||
bool empty() const { return Items.empty(); }
|
||||
size_t size() const { return Items.size(); }
|
||||
|
||||
auto begin() const { return Items.begin(); }
|
||||
auto end() const { return Items.end(); }
|
||||
|
||||
auto begin() { return Items.begin(); }
|
||||
auto end() { return Items.end(); }
|
||||
|
||||
void clear()
|
||||
{
|
||||
Id = 0;
|
||||
delete std::exchange(Value, nullptr);
|
||||
Items.clear();
|
||||
}
|
||||
};*/
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,499 @@
|
||||
#pragma once
|
||||
#include "Expression\Variable.h"
|
||||
#include "Include\Theme.h"
|
||||
#include <Resource.h>
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
/*static bool SHLoadIndirectString(const wchar_t *pszSource, wchar_t *pszOutBuf, uint32_t cchOutBuf)
|
||||
{
|
||||
return SUCCEEDED(DLL::Invoke<HRESULT>(L"shlwapi.dll", "SHLoadIndirectString",
|
||||
pszSource, pszOutBuf, cchOutBuf, nullptr));
|
||||
}*/
|
||||
|
||||
struct Package
|
||||
{
|
||||
string name;
|
||||
string path;
|
||||
string family;
|
||||
string id;
|
||||
string version;
|
||||
};
|
||||
|
||||
class PackagesCache
|
||||
{
|
||||
inline static const string _local_settings = LR"(Software\Classes\Local Settings)";
|
||||
inline static const string _packages = _local_settings + LR"(\Software\Microsoft\Windows\CurrentVersion\AppModel\Repository\Packages)";
|
||||
inline static const string _mrt_cache = _local_settings + LR"(\MrtCache)";
|
||||
|
||||
public:
|
||||
|
||||
std::vector<Package> list;
|
||||
|
||||
PackagesCache() = default;
|
||||
~PackagesCache() = default;
|
||||
|
||||
bool load()
|
||||
{
|
||||
HKEY hkeyPackages = nullptr;
|
||||
TResult res = ::RegOpenKeyExW(HKEY_CURRENT_USER, _packages, 0, KEY_ENUMERATE_SUB_KEYS | KEY_QUERY_VALUE, &hkeyPackages);
|
||||
|
||||
if(!res || !hkeyPackages)
|
||||
return false;
|
||||
|
||||
res = ERROR_SUCCESS;
|
||||
for(int i = 0; res.get() != ERROR_NO_MORE_ITEMS; i++)
|
||||
{
|
||||
string name(MAX_PATH);
|
||||
DWORD cchName = MAX_PATH;
|
||||
res = ::RegEnumKeyExW(hkeyPackages, i, name.data(), &cchName, nullptr, nullptr, nullptr, nullptr);
|
||||
if(res)
|
||||
{
|
||||
Package pk;
|
||||
pk.name = name.release(cchName);
|
||||
|
||||
HKEY hkeyPackage = nullptr;
|
||||
res = ::RegOpenKeyExW(hkeyPackages, name, 0, KEY_QUERY_VALUE, &hkeyPackage);
|
||||
if(res)
|
||||
{
|
||||
pk.id = name;// get_value(L"PackageID", hkeyPackage).move();
|
||||
//MBF(L"%s\n%s", pk.id.c_str(), name.c_str());
|
||||
if(!pk.id.empty())
|
||||
{
|
||||
pk.path = get_value(L"PackageRootFolder", hkeyPackage).move();
|
||||
//pk.name = get_value(L"DisplayName", hkeyPackage).move();
|
||||
get_name(&pk, hkeyPackage);
|
||||
|
||||
auto pos = pk.id.index_of(L'_');
|
||||
if(pos != pk.id.npos)
|
||||
{
|
||||
string _family_ = pk.id.substr(0, pos).move();
|
||||
string v = pk.id.substr(pos + 1).move();
|
||||
|
||||
pos = v.index_of(L'_');
|
||||
if(pos != v.npos)
|
||||
pk.version = v.substr(0, pos).move();
|
||||
|
||||
pos = pk.id.last_index_of(L'_');
|
||||
if(pos != pk.id.npos)
|
||||
{
|
||||
_family_ += pk.id.substr(pos);
|
||||
pk.family = _family_.move();
|
||||
}
|
||||
}
|
||||
list.push_back(std::move(pk));
|
||||
}
|
||||
::RegCloseKey(hkeyPackage);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
::RegCloseKey(hkeyPackages);
|
||||
hkeyPackages = nullptr;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
string get_value(const wchar_t *name, HKEY hkeyPackage)
|
||||
{
|
||||
if(hkeyPackage)
|
||||
{
|
||||
DWORD size = 0;
|
||||
DWORD type = REG_NONE;
|
||||
TResult res = ::RegQueryValueExW(hkeyPackage, name, 0, &type, nullptr, &size);
|
||||
if(res)
|
||||
{
|
||||
size_t length = size / sizeof(wchar_t);
|
||||
string buf(length);
|
||||
res = ::RegQueryValueExW(hkeyPackage, name, 0, &type, reinterpret_cast<LPBYTE>(buf.data()), &size);
|
||||
if(res)
|
||||
{
|
||||
return buf.release(length - 1).move();
|
||||
}
|
||||
}
|
||||
}
|
||||
return {};
|
||||
}
|
||||
|
||||
void get_name(Package *pk, HKEY hkeyPackage)
|
||||
{
|
||||
pk->name = get_value(L"DisplayName", hkeyPackage).move();
|
||||
|
||||
if(pk->name.length() > 3)
|
||||
{
|
||||
if(pk->name.starts_with(L"@{", false) &&
|
||||
pk->name.back(L'}', false))
|
||||
{
|
||||
wchar_t displayName[MAX_PATH]{};
|
||||
if(S_OK != ::SHLoadIndirectString(pk->name, displayName, MAX_PATH, nullptr) || pk->name.equals(displayName))
|
||||
{
|
||||
displayName[0] = 0;
|
||||
HKEY hkeyPackages_mrt = nullptr;
|
||||
TResult res = ::RegOpenKeyExW(HKEY_CURRENT_USER, _mrt_cache, 0, KEY_ENUMERATE_SUB_KEYS | KEY_QUERY_VALUE, &hkeyPackages_mrt);
|
||||
if(res)
|
||||
{
|
||||
for(int i = 0; res.get() != ERROR_NO_MORE_ITEMS; i++)
|
||||
{
|
||||
string name(MAX_PATH);
|
||||
DWORD cchName = MAX_PATH;
|
||||
res = ::RegEnumKeyExW(hkeyPackages_mrt, i, name.data(), &cchName, nullptr, nullptr, nullptr, nullptr);
|
||||
if(res)
|
||||
{
|
||||
name.release(cchName);
|
||||
if(name.contains(pk->id))
|
||||
{
|
||||
auto hkeyLang = get_langKey(hkeyPackages_mrt, name);
|
||||
if(hkeyLang)
|
||||
{
|
||||
for(i = 0; res.get() != ERROR_NO_MORE_ITEMS; i++)
|
||||
{
|
||||
wchar_t valueName[MAX_PATH]{};
|
||||
DWORD cbDisplayName = MAX_PATH;
|
||||
displayName[0] = 0;
|
||||
DWORD cchValueName = MAX_PATH;
|
||||
DWORD dtype = 0;
|
||||
res = ::RegEnumValueW(hkeyLang, i, valueName, &cchValueName, nullptr, &dtype, reinterpret_cast<LPBYTE>(displayName), &cbDisplayName);
|
||||
if(res && pk->name.equals(valueName))
|
||||
{
|
||||
pk->name = displayName;
|
||||
break;
|
||||
}
|
||||
}
|
||||
::RegCloseKey(hkeyLang);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
::RegCloseKey(hkeyPackages_mrt);
|
||||
}
|
||||
}
|
||||
pk->name = displayName;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
HKEY get_langKey(HKEY hkey, const wchar_t *subkey = nullptr)
|
||||
{
|
||||
HKEY result = nullptr;
|
||||
wchar_t name[MAX_PATH]{};
|
||||
DWORD cchName = MAX_PATH;
|
||||
HKEY hKeyLangList = nullptr;
|
||||
|
||||
TResult res = ::RegOpenKeyExW(hkey, subkey, 0, KEY_ENUMERATE_SUB_KEYS | KEY_QUERY_VALUE, &hKeyLangList);
|
||||
if(res)
|
||||
{
|
||||
res = ::RegEnumKeyExW(hKeyLangList, 0, name, &cchName, nullptr, nullptr, nullptr, nullptr);
|
||||
if(res)
|
||||
{
|
||||
HKEY hKeyLang = nullptr;
|
||||
res = ::RegOpenKeyExW(hKeyLangList, name, 0, KEY_ENUMERATE_SUB_KEYS | KEY_QUERY_VALUE, &hKeyLang);
|
||||
if(res)
|
||||
{
|
||||
name[0] = {};
|
||||
cchName = MAX_PATH;
|
||||
res = ::RegEnumKeyExW(hKeyLang, 0, name, &cchName, nullptr, nullptr, nullptr, nullptr);
|
||||
if(res)
|
||||
::RegOpenKeyExW(hKeyLang, name, 0, KEY_ENUMERATE_SUB_KEYS | KEY_QUERY_VALUE, &result);
|
||||
::RegCloseKey(hKeyLang);
|
||||
}
|
||||
}
|
||||
::RegCloseKey(hKeyLangList);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
const Package *find(const wchar_t *name) const
|
||||
{
|
||||
for(auto &pk : list)
|
||||
if(pk.id.contains(name))
|
||||
return &pk;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
bool exists(const wchar_t *name) const
|
||||
{
|
||||
return find(name);
|
||||
};
|
||||
};
|
||||
|
||||
class FontCache
|
||||
{
|
||||
std::unordered_map<uint32_t, Font*> fonts;
|
||||
HANDLE _handle{};
|
||||
|
||||
public:
|
||||
static constexpr auto Default = L"Nilesoft.Shell";
|
||||
static constexpr auto SegoeFluentIcons = L"Segoe Fluent Icons";
|
||||
static constexpr auto SegoeMDL2Assets = L"Segoe MDL2 Assets";
|
||||
|
||||
public:
|
||||
uint32_t _dpi = 96;
|
||||
//HFONT shell_font{};
|
||||
//HFONT default_font{};
|
||||
uint32_t default_id = 0;
|
||||
|
||||
FontCache()
|
||||
{
|
||||
}
|
||||
|
||||
~FontCache()
|
||||
{
|
||||
clear();
|
||||
if(_handle)
|
||||
::RemoveFontMemResourceEx(_handle);
|
||||
}
|
||||
|
||||
void init(HINSTANCE hinstance, uint32_t dpi = 96)
|
||||
{
|
||||
clear();
|
||||
_dpi = dpi;
|
||||
auto hRes = ::FindResourceW(hinstance, L"FONTICON", RT_RCDATA);
|
||||
if(!hRes)
|
||||
{
|
||||
Logger::Warning(L"FONTICON not found");
|
||||
return;
|
||||
}
|
||||
|
||||
auto hResData = ::LoadResource(hinstance, hRes);
|
||||
if(hResData)
|
||||
{
|
||||
auto lpFileView = ::LockResource(hResData);
|
||||
if(lpFileView)
|
||||
{
|
||||
auto cjSize = ::SizeofResource(hinstance, hRes);
|
||||
DWORD numFonts = 0;
|
||||
_handle = ::AddFontMemResourceEx(lpFileView, cjSize, nullptr, &numFonts);
|
||||
if(_handle)
|
||||
{
|
||||
//shell_font = add(Default, 16);
|
||||
}
|
||||
UnlockResource(lpFileView);
|
||||
}
|
||||
::FreeResource(hResData);
|
||||
}
|
||||
}
|
||||
|
||||
//icon.Fluent()
|
||||
/*void add_default(const string &name, long size)
|
||||
{
|
||||
if(name.empty())
|
||||
{
|
||||
default_font = add(SegoeFluentIcons, size);
|
||||
if(!default_font)
|
||||
{
|
||||
default_font = add(SegoeMDL2Assets, size);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
default_font = add(name, size);
|
||||
}
|
||||
}*/
|
||||
|
||||
Font *at(uint32_t id) const
|
||||
{
|
||||
for(auto &font : fonts)
|
||||
{
|
||||
if(id == font.first) return font.second;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
Font *at(HFONT hfont) const
|
||||
{
|
||||
for(auto font : fonts)
|
||||
{
|
||||
if(hfont == font.second->get())
|
||||
return font.second;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
bool remove(HFONT hfont)
|
||||
{
|
||||
for(auto font = fonts.begin(); font != fonts.end(); font++)
|
||||
{
|
||||
if(hfont == font->second->get())
|
||||
{
|
||||
fonts.erase(font);
|
||||
break;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
HFONT add(const string &name, int size, int charset = DEFAULT_CHARSET)
|
||||
{
|
||||
size = Theme::DPI(size, _dpi);
|
||||
auto id = Hash::dohash(size, name.hash());
|
||||
auto font = at(id);
|
||||
if(!font)
|
||||
{
|
||||
font = new Font(name, size, CLEARTYPE_QUALITY, charset);
|
||||
if(font->get())
|
||||
fonts[id] = font;
|
||||
else
|
||||
{
|
||||
delete font;
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
return font ? font->get() : nullptr;
|
||||
}
|
||||
|
||||
HFONT add(const string &name, int size, uint32_t dpi, int charset = DEFAULT_CHARSET)
|
||||
{
|
||||
//size = Theme::DPI(size, _dpi);
|
||||
auto id = Hash::dohash(size + dpi, name.hash());
|
||||
auto font = at(id);
|
||||
if(!font)
|
||||
{
|
||||
font = new Font(name, size, CLEARTYPE_QUALITY, charset);
|
||||
if(font->get())
|
||||
fonts[id] = font;
|
||||
else
|
||||
{
|
||||
delete font;
|
||||
return nullptr;
|
||||
}
|
||||
}
|
||||
return font ? font->get() : nullptr;
|
||||
}
|
||||
|
||||
void clear()
|
||||
{
|
||||
for(auto font : fonts)
|
||||
delete font.second;
|
||||
|
||||
fonts.clear();
|
||||
//default_font = {};
|
||||
//shell_font = {};
|
||||
default_id = {};
|
||||
}
|
||||
|
||||
size_t size() const { return fonts.size(); }
|
||||
};
|
||||
|
||||
struct ImageCache
|
||||
{
|
||||
std::vector<uint32_t> id;
|
||||
auto_expr value;
|
||||
|
||||
bool equals(uint32_t ident) const
|
||||
{
|
||||
for(auto &it : id)
|
||||
{
|
||||
if(it == ident) return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool equals(std::vector<uint32_t> const &idents) const
|
||||
{
|
||||
for(auto& i : idents)
|
||||
{
|
||||
if(equals(i)) return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void add(uint32_t ident)
|
||||
{
|
||||
for(auto &it : id)
|
||||
if(it == ident) return;
|
||||
id.push_back(ident);
|
||||
}
|
||||
|
||||
void add(std::vector<uint32_t> ids)
|
||||
{
|
||||
for(auto &it : ids) add(it);
|
||||
}
|
||||
};
|
||||
|
||||
struct CACHE
|
||||
{
|
||||
Settings settings;
|
||||
|
||||
struct {
|
||||
Scope global;
|
||||
Scope runtime;
|
||||
Scope loc;
|
||||
} variables;
|
||||
|
||||
std::vector<NativeMenu*> statics;
|
||||
NativeMenu dynamic;
|
||||
FontCache fonts;
|
||||
PackagesCache Packages;
|
||||
std::vector<ImageCache> images;
|
||||
|
||||
struct
|
||||
{
|
||||
uint32_t color = IDENT_DEFAULT;
|
||||
uint32_t back = IDENT_DEFAULT;
|
||||
string name = FontCache::Default;
|
||||
}
|
||||
glyph;
|
||||
|
||||
|
||||
CACHE()
|
||||
{
|
||||
//runtime_variables.Parent = &variables;
|
||||
}
|
||||
|
||||
~CACHE()
|
||||
{
|
||||
while(!statics.empty())
|
||||
{
|
||||
delete statics.back();
|
||||
statics.pop_back();
|
||||
}
|
||||
|
||||
images.clear();
|
||||
|
||||
variables.global.clear(true);
|
||||
variables.runtime.clear(true);
|
||||
variables.loc.clear(true);
|
||||
|
||||
Packages.list.clear();
|
||||
}
|
||||
|
||||
void reload(uint32_t dpi = 96)
|
||||
{
|
||||
fonts.clear();
|
||||
fonts._dpi = dpi;
|
||||
fonts.add(glyph.name, Theme::SystemMetrics(SM_CXSMICON, dpi));
|
||||
}
|
||||
|
||||
Expression *get_image(uint32_t id)
|
||||
{
|
||||
for(auto &si : images)
|
||||
{
|
||||
if(si.equals(id))
|
||||
return si.value;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void add_image(std::vector<uint32_t> &&ids, Expression *e)
|
||||
{
|
||||
if(e)
|
||||
{
|
||||
for(auto &img : images)
|
||||
{
|
||||
if(img.equals(ids))
|
||||
{
|
||||
img.add(ids);
|
||||
img.value = e;
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
images.emplace_back(std::move(ids), e);
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,836 @@
|
||||
#pragma once
|
||||
|
||||
//constexpr auto WC_MENU_Layer = L"Nilesoft.Shell.Window.Layers";
|
||||
//constexpr auto WC_MENU_Layers = L"Nilesoft.Shell.Window.Border";
|
||||
//constexpr auto WC_MENU_Layers = L"Nilesoft.Shell.Window.Shadow";
|
||||
constexpr auto WC_Shell_Window = L"Nilesoft.Shell.Window";
|
||||
constexpr auto def_COMSPEC = L"ComSpec";
|
||||
constexpr auto def_EXPLORER = L"explorer.exe";
|
||||
constexpr auto def_POWERSHELL = L"powershell.exe";
|
||||
constexpr auto def_PWSH = L"pwsh.exe";
|
||||
constexpr auto UxSubclass = L"UxSubclass";
|
||||
constexpr auto Windows_UI_FileExplorer = L"Windows.UI.FileExplorer.dll";
|
||||
|
||||
#include "Include/Theme.h"
|
||||
#include <Library/PlutoVGWrap.h>
|
||||
#include "Include/Tip.h"
|
||||
#include <stack>
|
||||
|
||||
#define MF_ALLSTATE 0x00FF
|
||||
#define MF_MAINMENU 0xFFFF
|
||||
#define MFMWFP_OFFMENU 0
|
||||
#define MFMWFP_MAINMENU 0x0000FFFF
|
||||
#define MFMWFP_NOITEM 0xFFFFFFFF
|
||||
#define MFMWFP_UPARROW 0xFFFFFFFD //Warning: Also used to define IDSYS_MNUP
|
||||
#define MFMWFP_DOWNARROW 0xFFFFFFFC //Warning: Also used to define IDSYS_MNDOWN
|
||||
#define MFMWFP_MINVALID 0xFFFFFFFC
|
||||
#define MFMWFP_ALTMENU 0xFFFFFFFB
|
||||
#define MFMWFP_FIRSTITEM 0
|
||||
|
||||
#define MNUS_DEFAULT 0x00000001
|
||||
#define MNUS_DELETE 0x00000002
|
||||
#define MNUS_DRAWFRAME 0x00000004
|
||||
|
||||
// This tells xxxMNItemSize that the bitamp size is not avilable
|
||||
#define MNIS_MEASUREBMP -1
|
||||
|
||||
|
||||
//MN_SIZEWINDOW wParam flag. xxxMNUpdateShownMenu sends this message, so keep MNSW_ and MNUS_ in sync.
|
||||
|
||||
#define MNSW_RETURNSIZE 0
|
||||
#define MNSW_SIZE MNUS_DEFAULT
|
||||
#define MNSW_DRAWFRAME MNUS_DRAWFRAME
|
||||
|
||||
//
|
||||
// System timer IDs
|
||||
//
|
||||
#define IDSYS_LAYER 0x0000FFF5L
|
||||
#define IDSYS_FADE 0x0000FFF6L
|
||||
#define IDSYS_WNDTRACKING 0x0000FFF7L
|
||||
#define IDSYS_FLASHWND 0x0000FFF8L
|
||||
#define IDSYS_MNAUTODISMISS 0x0000FFF9L
|
||||
#define IDSYS_MOUSEHOVER 0x0000FFFAL
|
||||
#define IDSYS_MNANIMATE 0x0000FFFBL
|
||||
#define IDSYS_MNDOWN MFMWFP_DOWNARROW // 0xFFFFFFFC
|
||||
#define IDSYS_LBSEARCH 0x0000FFFCL
|
||||
#define IDSYS_MNUP MFMWFP_UPARROW // 0xFFFFFFFD
|
||||
#define IDSYS_STANIMATE 0x0000FFFDL
|
||||
#define IDSYS_MNSHOW 0x0000FFFEL
|
||||
#define IDSYS_SCROLL 0x0000FFFEL
|
||||
#define IDSYS_MNHIDE 0x0000FFFFL
|
||||
#define IDSYS_CARET 0x0000FFFFL
|
||||
|
||||
|
||||
//EXTERN_C LRESULT CALLBACK TaskBarSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
|
||||
LRESULT WINAPI LayerProc(HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam);
|
||||
|
||||
//EXTERN_C LRESULT __stdcall TaskBarSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData);
|
||||
|
||||
//#include <stack>
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
constexpr auto NILESOFTSHELL = 0x1E34270FU;
|
||||
static const uintptr_t CONTEXTMENUSUBCLASS = NILESOFTSHELL;
|
||||
static const uintptr_t CONTEXTMENUSUBCLASS_TASKBAR = NILESOFTSHELL + 1;
|
||||
|
||||
struct menuitem_t
|
||||
{
|
||||
uint32_t type = 0;
|
||||
uint32_t wid = 0;
|
||||
uint32_t hash = 0;
|
||||
MUID *ui = nullptr;
|
||||
string name;
|
||||
string title;
|
||||
string keys;
|
||||
uint32_t length = 0;
|
||||
int tab = 0;
|
||||
bool disabled = false;
|
||||
bool radio_check = false;
|
||||
int checked = 0;
|
||||
ULONG_PTR dwItemData = 0;
|
||||
HBITMAP image = nullptr;
|
||||
menuitem_t *parent = nullptr;
|
||||
string path;
|
||||
Position position = Position::Auto;
|
||||
Visibility visibility = Visibility::Enabled;
|
||||
std::vector<NativeMenu*> native_items;
|
||||
std::vector<menuitem_t *> items;
|
||||
bool is_toplevel = false;
|
||||
~menuitem_t()
|
||||
{
|
||||
for(auto item : items)
|
||||
delete item;
|
||||
}
|
||||
|
||||
bool is_separator() const { return type == 2; }
|
||||
bool is_menu() const { return type == 1; }
|
||||
|
||||
uint32_t uid() const { return ui ? ui->id : hash; }
|
||||
};
|
||||
|
||||
struct WND
|
||||
{
|
||||
struct window_t
|
||||
{
|
||||
HWND handle{};
|
||||
Rect rect;
|
||||
|
||||
long x{};
|
||||
long y{};
|
||||
long width{};
|
||||
long height{};
|
||||
bool visible{};
|
||||
HBITMAP hbitmap{};
|
||||
|
||||
void destroy()
|
||||
{
|
||||
if(handle)
|
||||
::DestroyWindow(handle);
|
||||
if(hbitmap)
|
||||
::DeleteObject(hbitmap);
|
||||
handle = {};
|
||||
hbitmap = {};
|
||||
}
|
||||
|
||||
bool create(long x, long y, long width, long height, HWND hOwner, uint32_t ex_style = 0)
|
||||
{
|
||||
handle = ::CreateWindowExW(WS_EX_TOPMOST | WS_EX_TOOLWINDOW | WS_EX_TRANSPARENT | WS_EX_NOACTIVATE | ex_style,
|
||||
WC_Shell_Window, nullptr, WS_POPUP,
|
||||
x, y,
|
||||
width, height,
|
||||
hOwner, nullptr, Path::GetCurrentModule(), nullptr);
|
||||
return handle;
|
||||
}
|
||||
|
||||
bool regoin(uint8_t radius = 0) const {
|
||||
return WND::Regoin(handle, 0, 0, width + 1, height + 1, radius);
|
||||
}
|
||||
|
||||
void hidden()
|
||||
{
|
||||
if(handle)
|
||||
{
|
||||
//ShowWindowAsync()
|
||||
if(::ShowWindow(handle, SW_HIDE))
|
||||
visible = false;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
window_t layer;
|
||||
window_t blurry;
|
||||
|
||||
HWND handle{};
|
||||
HDC hdc{};
|
||||
Rect rect;
|
||||
HMENU hMenu{};
|
||||
//CriticalSection cs;
|
||||
bool visible_layers = false;
|
||||
long x{};
|
||||
long y{};
|
||||
long width{};
|
||||
long height{};
|
||||
bool visible = true;
|
||||
bool has_scroll = false;
|
||||
bool scrolled = false;
|
||||
bool de = true;
|
||||
HBITMAP hbitmap{};
|
||||
ContextMenu *ctx{};
|
||||
|
||||
HWND dr = 0;
|
||||
|
||||
D2D d2d;
|
||||
WND(HWND hWnd = nullptr) : handle{ hWnd }
|
||||
{
|
||||
//cs.lock();
|
||||
}
|
||||
|
||||
void destroy()
|
||||
{
|
||||
//cs.unlock();
|
||||
blurry.destroy();
|
||||
layer.destroy();
|
||||
if(hbitmap) ::DeleteObject(hbitmap);
|
||||
if(hdc) ::ReleaseDC(handle, hdc);
|
||||
hbitmap = {};
|
||||
handle = {};
|
||||
}
|
||||
|
||||
void hidden()
|
||||
{
|
||||
//ShowWindowAsync()
|
||||
blurry.hidden();
|
||||
layer.hidden();
|
||||
if(handle)
|
||||
{
|
||||
if(::ShowWindow(handle, SW_HIDE))
|
||||
visible = false;
|
||||
}
|
||||
}
|
||||
|
||||
bool show_layers()
|
||||
{
|
||||
if(!visible_layers)
|
||||
{
|
||||
// SWP_NOOWNERZORDER = Does not change the owner window's position in the Z order.
|
||||
// SWP_NOZORDER = Retains the current Z order (ignores the hWndInsertAfter parameter).
|
||||
// | SWP_NOSENDCHANGING | SWP_NOCOPYBITS | SWP_NOREDRAW
|
||||
auto flags = SWP_NOMOVE | SWP_NOSIZE | SWP_NOZORDER | SWP_NOOWNERZORDER | SWP_NOREDRAW | SWP_NOACTIVATE | SWP_SHOWWINDOW;
|
||||
|
||||
auto hWinPosInfo = ::BeginDeferWindowPos((layer.handle != nullptr) + (blurry.handle != nullptr));
|
||||
if(hWinPosInfo)
|
||||
{
|
||||
if(layer.handle)
|
||||
{
|
||||
hWinPosInfo = ::DeferWindowPos(hWinPosInfo, layer.handle, nullptr, 0, 0, 0, 0, flags);
|
||||
layer.visible = true;
|
||||
}
|
||||
|
||||
if(blurry.handle)
|
||||
{
|
||||
hWinPosInfo = ::DeferWindowPos(hWinPosInfo, blurry.handle, nullptr, 0, 0, 0, 0, flags);
|
||||
blurry.visible = true;
|
||||
}
|
||||
|
||||
if(hWinPosInfo)
|
||||
::EndDeferWindowPos(hWinPosInfo);
|
||||
|
||||
::SetWindowPos(handle, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOMOVE | SWP_NOSIZE | SWP_NOOWNERZORDER |SWP_NOREDRAW | SWP_NOACTIVATE | SWP_SHOWWINDOW);
|
||||
//::ShowWindowAsync(handle, SW_HIDE);
|
||||
}
|
||||
|
||||
visible_layers = layer.visible || blurry.visible;
|
||||
}
|
||||
return visible_layers;
|
||||
}
|
||||
|
||||
bool regoin(uint8_t radius = 0) const {
|
||||
return Regoin(handle, 0, 0, width + 1, height + 1, radius);
|
||||
}
|
||||
|
||||
bool set_prop() {
|
||||
return ::SetPropW(handle, L"wnd", this);
|
||||
}
|
||||
|
||||
static WND *get_prop(HWND hWnd) {
|
||||
return (WND *)::GetPropW(hWnd, L"wnd");
|
||||
}
|
||||
|
||||
static bool Regoin(HWND hWnd, int x, int y, int width, int height, int radius = 0)
|
||||
{
|
||||
radius += radius + (radius >= 8 ? 2 : 1);
|
||||
auto ret = false;
|
||||
HRGN hRegion{};
|
||||
if(radius > 0)
|
||||
hRegion = ::CreateRoundRectRgn(x, y, width, height, radius, radius);
|
||||
else
|
||||
hRegion = ::CreateRectRgn(x, y, width, height);
|
||||
|
||||
if(hRegion)
|
||||
{
|
||||
ret = ::SetWindowRgn(hWnd, hRegion, 0);
|
||||
::DeleteObject(hRegion);
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
};
|
||||
|
||||
/*
|
||||
plutovg_move_to(pluto, start.x, start.y);
|
||||
plutovg_line_to(pluto, end.x, end.y);
|
||||
plutovg_set_source_rgb(pluto, color_branch.r / 255.0,
|
||||
color_branch.g / 255.0,
|
||||
color_branch.b / 255.0);
|
||||
plutovg_set_line_width(pluto, width_delta_stack[sp] > line_width
|
||||
? width_delta_stack[sp]
|
||||
: line_width);
|
||||
plutovg_stroke(pluto);
|
||||
|
||||
|
||||
plutovg_surface_t *const pluto_surface =
|
||||
plutovg_surface_create(IMG_SIZE, IMG_SIZE);
|
||||
plutovg_t *const pluto = plutovg_create(pluto_surface);
|
||||
|
||||
// Add background to image.
|
||||
plutovg_gradient_t *const gradient = plutovg_gradient_create_linear(
|
||||
IMG_SIZE / 2U, 0U, IMG_SIZE / 2U, IMG_SIZE);
|
||||
for(uint8_t stop_idx = 0U; stop_idx < sizeof(stops) / sizeof(stops[0]);
|
||||
++stop_idx)
|
||||
{
|
||||
plutovg_gradient_add_stop_rgb(
|
||||
gradient, stops[stop_idx], colors[stop_idx].r / 255.0,
|
||||
colors[stop_idx].g / 255.0, colors[stop_idx].b / 255.0);
|
||||
}
|
||||
plutovg_rect(pluto, 0U, 0U, IMG_SIZE, IMG_SIZE);
|
||||
plutovg_set_source_gradient(pluto, gradient);
|
||||
plutovg_fill(pluto);
|
||||
*/
|
||||
|
||||
|
||||
class ContextMenu
|
||||
{
|
||||
public:
|
||||
//size_t cbsize = sizeof(ContextMenu);
|
||||
struct Prop
|
||||
{
|
||||
static bool Set(HWND handle, ContextMenu *ctx)
|
||||
{
|
||||
return ::SetPropW(handle, CLS_Shell, ctx);
|
||||
}
|
||||
|
||||
template<typename T = ContextMenu *>
|
||||
static T Get(HWND handle)
|
||||
{
|
||||
return reinterpret_cast<T>(::GetPropW(handle, CLS_Shell));
|
||||
}
|
||||
|
||||
static bool Remove(HWND handle)
|
||||
{
|
||||
return handle ? ::RemovePropW(handle, CLS_Shell) : false;
|
||||
}
|
||||
};
|
||||
|
||||
struct menu_t
|
||||
{
|
||||
enum {
|
||||
MFT_UNDEFINED = -1,
|
||||
MFT_SYSTEM = 0,
|
||||
MFT_DYNAMIC = 1
|
||||
};
|
||||
|
||||
HMENU handle{};
|
||||
uint32_t id{};
|
||||
uint32_t hash{};
|
||||
|
||||
int level = -1;
|
||||
int type = -1;
|
||||
bool is_main{};
|
||||
bool destory{};
|
||||
bool has_col{};
|
||||
HWND wnd{};
|
||||
MenuItemInfo *owner{};
|
||||
long popup_height{};
|
||||
string path;
|
||||
|
||||
std::vector<MenuItemInfo *> statics;
|
||||
std::vector<NativeMenu *> dynamics;
|
||||
|
||||
std::vector<menuitem_t *> *std_items = nullptr;
|
||||
|
||||
NativeMenu *parent{};
|
||||
//bool dynamic{};
|
||||
|
||||
struct
|
||||
{
|
||||
uint32_t id{};
|
||||
uint32_t length{};
|
||||
long width{};
|
||||
long height{};
|
||||
//uint16_t dispaly = 0;
|
||||
uint16_t images{};
|
||||
uint16_t checks{};
|
||||
uint16_t popups{};
|
||||
bool has_tap{};
|
||||
bool has_align() const { return checks || images; }
|
||||
} draw;
|
||||
|
||||
bool is_dynamic() const
|
||||
{
|
||||
return owner ? owner->dynamic : false;
|
||||
}
|
||||
};
|
||||
|
||||
struct PositionList
|
||||
{
|
||||
std::vector<MenuItemInfo*> Top;
|
||||
std::vector<MenuItemInfo*> Middle;
|
||||
std::vector<MenuItemInfo*> Bottom;
|
||||
std::vector<MenuItemInfo*> Auto;
|
||||
std::vector<MenuItemInfo*> Custom;
|
||||
|
||||
void push(auto item)
|
||||
{
|
||||
switch(item->position)
|
||||
{
|
||||
case Position::Top:
|
||||
Top.push_back(item);
|
||||
break;
|
||||
case Position::Middle:
|
||||
Middle.push_back(item);
|
||||
break;
|
||||
case Position::Bottom:
|
||||
Bottom.push_back(item);
|
||||
break;
|
||||
case Position::Auto:
|
||||
case Position::None:
|
||||
Auto.push_back(item);
|
||||
break;
|
||||
default:
|
||||
Custom.push_back(item);
|
||||
break;
|
||||
}
|
||||
};
|
||||
|
||||
auto size() const { return Top.size() + Middle.size() + Bottom.size() + Auto.size() + Custom.size(); }
|
||||
|
||||
static bool is_id(uint32_t id, const MenuItemInfo *item) {
|
||||
return item && item->hash == id;
|
||||
}
|
||||
};
|
||||
|
||||
struct ID
|
||||
{
|
||||
//0x03000012
|
||||
//static constexpr auto Sys = (0xffffffff - 0x00000fff);
|
||||
//static constexpr auto Max = (0xffffffff - 0x00000fff);
|
||||
//static constexpr auto Min = (0xffffffff - 0x0000ffff);
|
||||
//static constexpr auto Start = (0xffffffff - 0x0000ffffu); //65535
|
||||
//firstUniqueID
|
||||
//60007
|
||||
static constexpr auto start_id = 0x0fffffff; //0-65535
|
||||
static constexpr auto start_sys = 0x5fffffff;
|
||||
|
||||
uint32_t sys = start_sys;
|
||||
uint32_t id = start_id;
|
||||
|
||||
uint32_t get_id() { return id++; }
|
||||
uint32_t get_sys() { return sys++; }
|
||||
|
||||
bool equals(uint32_t ident) const
|
||||
{
|
||||
return(ident >= start_id && ident < start_sys);
|
||||
}
|
||||
|
||||
} ident;
|
||||
|
||||
public:
|
||||
ContextMenu(const ContextMenu &) = delete;
|
||||
ContextMenu(HWND hWnd, HMENU hMenu, Point const &pt);
|
||||
~ContextMenu();
|
||||
|
||||
public:
|
||||
/*
|
||||
// system window1
|
||||
CabinetWClass
|
||||
(null)
|
||||
#32769
|
||||
CabinetWClass
|
||||
CabinetWClass
|
||||
|
||||
// system window2
|
||||
WorkerW
|
||||
CabinetWClass
|
||||
CabinetWClass
|
||||
CabinetWClass
|
||||
CabinetWClass
|
||||
|
||||
// system window3
|
||||
ReBarWindow32
|
||||
WorkerW
|
||||
WorkerW
|
||||
CabinetWClass
|
||||
CabinetWClass
|
||||
|
||||
|
||||
---------------
|
||||
//column options menu
|
||||
DirectUIHWND
|
||||
SHELLDLL_DefView
|
||||
SHELLDLL_DefView
|
||||
CabinetWClass
|
||||
CabinetWClass
|
||||
|
||||
|
||||
---------------------------
|
||||
// back menu
|
||||
TravelBand
|
||||
ReBarWindow32
|
||||
ReBarWindow32
|
||||
CabinetWClass
|
||||
CabinetWClass
|
||||
|
||||
---------------------------
|
||||
// Breadcrumb menu
|
||||
Breadcrumb Parent
|
||||
msctls_progress32
|
||||
msctls_progress32
|
||||
CabinetWClass
|
||||
CabinetWClass
|
||||
|
||||
|
||||
win10->taskbar->datetime
|
||||
Shell_Trayind
|
||||
(null)
|
||||
#32769
|
||||
Shell_Trayind
|
||||
Shell_Trayind
|
||||
|
||||
win10->taskbar->start
|
||||
LauncherTipWnd
|
||||
(null)
|
||||
#32769
|
||||
LauncherTipWnd
|
||||
LauncherTipWnd
|
||||
|
||||
// remove properties
|
||||
DirectUIHWND
|
||||
DUIViewWndClassName
|
||||
DUIViewWndClassName
|
||||
CabinetWClass
|
||||
CabinetWClass
|
||||
*/
|
||||
|
||||
// save screenshots
|
||||
struct ss_t
|
||||
{
|
||||
HBITMAP hbitmap;
|
||||
Rect rc;
|
||||
};
|
||||
std::vector<ss_t> _level_bitmap;
|
||||
|
||||
struct {
|
||||
HWND owner{};
|
||||
HWND active{};
|
||||
HWND focus{};
|
||||
}hwnd;
|
||||
|
||||
struct {
|
||||
bool activated{};
|
||||
bool DwmEnabled{};
|
||||
explicit operator bool() const { return DwmEnabled && activated; }
|
||||
} composition;
|
||||
|
||||
struct {
|
||||
HFONT handle{};
|
||||
LOGFONTW menu{};
|
||||
Font icon;
|
||||
Font icon10;
|
||||
}font;
|
||||
|
||||
struct symbole_tag
|
||||
{
|
||||
SIZE size{};
|
||||
HBITMAP normal{};
|
||||
HBITMAP normal_disabled{};
|
||||
HBITMAP select{};
|
||||
HBITMAP select_disabled{};
|
||||
|
||||
~symbole_tag()
|
||||
{
|
||||
if(normal) ::DeleteObject(normal);
|
||||
if(normal_disabled) ::DeleteObject(normal_disabled);
|
||||
if(select) ::DeleteObject(select);
|
||||
if(select_disabled) ::DeleteObject(select_disabled);
|
||||
}
|
||||
};
|
||||
|
||||
struct {
|
||||
symbole_tag chevron;
|
||||
symbole_tag checked;
|
||||
symbole_tag bullet;
|
||||
}symbol;
|
||||
|
||||
struct {
|
||||
|
||||
struct {
|
||||
bool enabled = true;
|
||||
bool title = true;
|
||||
bool visibility = true;
|
||||
bool parent = true;
|
||||
bool separator = true;
|
||||
bool keys = true;
|
||||
int image = 1;
|
||||
int position = 1;
|
||||
|
||||
struct
|
||||
{
|
||||
bool duplicate = false;
|
||||
bool disabled = false;
|
||||
bool separator = false;
|
||||
}remove;
|
||||
|
||||
} modify_items;
|
||||
|
||||
struct {
|
||||
bool enabled = true;
|
||||
bool image = true;
|
||||
bool keys = true;
|
||||
} new_items;
|
||||
|
||||
} _settings;
|
||||
|
||||
struct
|
||||
{
|
||||
HWND hWnd{};
|
||||
HMENU hMenu{};
|
||||
menu_t *menu{};
|
||||
//uint32_t level{};
|
||||
uint32_t selectitem_pos = MF_NOITEM;//SELECTITEM
|
||||
MenuItemInfo *selectitem{};
|
||||
MenuItemInfo *select_previtem{};
|
||||
MenuItemInfo *tip{};
|
||||
RECT rect{};
|
||||
HDC hdc{};
|
||||
uint32_t selectid{};
|
||||
|
||||
void zero()
|
||||
{
|
||||
hWnd = {};
|
||||
hMenu = {};
|
||||
menu={};
|
||||
//level = 0;
|
||||
selectitem_pos = MF_NOITEM;
|
||||
selectitem = {};
|
||||
select_previtem = {};
|
||||
selectid = {};
|
||||
hdc = {};
|
||||
}
|
||||
|
||||
} current;
|
||||
|
||||
struct oooo
|
||||
{
|
||||
HMENU hmenu{};
|
||||
HWND hwnd{};
|
||||
HWND hdc{};
|
||||
};
|
||||
|
||||
std::unordered_map<HMENU, oooo> map_menu_wnd;
|
||||
|
||||
uint8_t mouse_button = 0;
|
||||
uint32_t selectid = 0;
|
||||
Keyboard keyboard;
|
||||
Context _context;
|
||||
Window _window;
|
||||
MESSAGE msg{};
|
||||
|
||||
DPI dpi;
|
||||
bool common = true;
|
||||
CACHE *_cache{};
|
||||
Visibility _vis = Visibility::Normal;
|
||||
|
||||
std::vector<uint32_t> parent_level;
|
||||
struct
|
||||
{
|
||||
std::vector<MenuItemInfo *> statics;
|
||||
std::vector<MenuItemInfo *> dynamics;
|
||||
}
|
||||
_moved_items;
|
||||
|
||||
MenuItemInfo *invoke_item{};
|
||||
std::vector<MenuItemInfo *> _items;
|
||||
std::vector<MenuItemInfo *> _items_command;
|
||||
std::vector<MenuItemInfo *> _items_popup;
|
||||
|
||||
std::vector<MenuItemInfo *> _main_popup;
|
||||
std::unordered_map<HMENU, menu_t> _menus;
|
||||
|
||||
WinEventHook _winEventHook;
|
||||
WindowsHook _keyboardHook;
|
||||
WindowSubclass _windowSubclass;
|
||||
|
||||
Theme _theme;
|
||||
HMENU _hMenu = nullptr;
|
||||
HMENU _hMenu_original = nullptr;
|
||||
HTHEME _hTheme{};
|
||||
HBRUSH _hbackground{};
|
||||
HBRUSH _hbackground0{};
|
||||
HCURSOR hCursor{};
|
||||
uint32_t _showdelay[2]{ UINT32_MAX, UINT32_MAX };
|
||||
Rect _rcMonitor{};
|
||||
LANGID languageId = 0;
|
||||
int is_layoutRTL = 0;
|
||||
Tip _tip;
|
||||
string _screenshot;
|
||||
|
||||
HINSTANCE hInstance{};
|
||||
Selections Selected;
|
||||
|
||||
DWORD ProcessId{};
|
||||
DWORD ThreadId{};
|
||||
|
||||
std::vector<WND *> _level;
|
||||
std::unordered_map<HWND, WND> _map;
|
||||
GC<MenuItemInfo> _gc;
|
||||
bool _uninitialized = false;
|
||||
|
||||
menuitem_t *__system_menu_tree = nullptr;
|
||||
std::unordered_map<uint32_t, menuitem_t *> __map_system_menu;
|
||||
|
||||
std::vector<menuitem_t *> __movable_system_items;
|
||||
|
||||
public:// functions
|
||||
|
||||
bool set_prop(auto hWnd) { return Prop::Set(hWnd, this); }
|
||||
ContextMenu *get_prop(auto hWnd) { return Prop::Get(hWnd); }
|
||||
|
||||
void init_cfg();
|
||||
bool prepare_new_items(PositionList &posList, const std::vector<NativeMenu *> &list, MenuItemInfo *owner, menu_t *menu, bool moved = false);
|
||||
bool prepare_system_items(PositionList &list, menu_t *menu);
|
||||
bool prepare_system_items2(PositionList &list, menu_t *menu);
|
||||
|
||||
void prepare_system_item(menuitem_t *item, MenuItemInfo *mii, menu_t *menu);
|
||||
|
||||
|
||||
LRESULT OnTimer(UINT_PTR nIDEvent, TIMERPROC Timerproc = nullptr);
|
||||
LRESULT OnStart();
|
||||
LRESULT OnEnd();
|
||||
|
||||
LRESULT OnInitMenu(HMENU hMenu);
|
||||
LRESULT OnInitMenuPopup(HMENU hMenu, uint32_t uPosition);
|
||||
LRESULT OnUninitMenuPopup(HMENU hMenu);
|
||||
LRESULT OnMenuSelect(HMENU hMenu, uint32_t id, uint32_t flags);
|
||||
LRESULT OnDrawItem(DRAWITEMSTRUCT *di);
|
||||
LRESULT OnMeasureItem(MEASUREITEMSTRUCT *mi);
|
||||
|
||||
LRESULT OnDrawItem_D2D(DRAWITEMSTRUCT *di);
|
||||
|
||||
uint32_t invoke(CommandProperty *cmd_prop);
|
||||
bool is_excluded();
|
||||
bool Initialize();
|
||||
int Uninitialize();
|
||||
int InvokeCommand(int id);
|
||||
void build_system_menuitems(HMENU hMenu, menuitem_t *menu, bool is_root = false);
|
||||
void build_main_system_menuitems(menuitem_t *menu, bool is_root = false);
|
||||
|
||||
|
||||
void backup_native_items(HMENU hMenu, uint32_t id, bool check = false);
|
||||
|
||||
WND *OnMenuCreate(HWND hWnd);
|
||||
void OnMenuShow(HWND hWnd, WND *wnd = nullptr);
|
||||
bool CreateLayer(WND *wnd);
|
||||
void UpdateLayered(WND *wnd, bool update_blurry = false);
|
||||
bool draw_layer(WND *wnd, SIZE size, int margin);
|
||||
void screenshot();
|
||||
|
||||
HMENU MenuHandle() const;
|
||||
|
||||
/*template<typename T = long>
|
||||
T dpi(auto value) const { return static_cast<T>(std::rint(value * double(_dpi) / 96.0)); }
|
||||
|
||||
template<typename T = long>
|
||||
T original_dpi(auto value) const { return static_cast<T>(std::rint(value * double(_odpi) / 96.0)); }
|
||||
|
||||
long xdpi(auto value) const
|
||||
{
|
||||
return static_cast<long>(std::rint(value * double(_dpi) / double(_odpi)));
|
||||
}
|
||||
*/
|
||||
void draw_string(HDC hdc, HFONT hFont, const Rect *rc, const Color &color, const wchar_t *text, int length = -1, DWORD format = 0, bool disable_BufferedPaint = false);
|
||||
|
||||
public:
|
||||
// static variables
|
||||
inline static std::unordered_map<ContextMenu *, bool> Processes;
|
||||
inline static bool FontNotFound = false;
|
||||
inline static POINT point = {};
|
||||
inline static std::unordered_map<HWINEVENTHOOK, ContextMenu *> HookMap;
|
||||
|
||||
public:
|
||||
// static functions
|
||||
inline static void draw_rect(DC *dc, const POINT &pt, const SIZE &size, const Color &color, const Color &border = {}, int radius = 0);
|
||||
|
||||
static void __stdcall Invoke(ContextMenu *cm);
|
||||
/*static LRESULT __stdcall TipProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam,
|
||||
UINT_PTR uIdSubclass, DWORD_PTR dwRefData);*/
|
||||
static LRESULT __stdcall WindowSubclassProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam,
|
||||
UINT_PTR uIdSubclass, DWORD_PTR dwRefData);
|
||||
//static LRESULT __stdcall MenuProc(HWND hWnd, uint32_t uMsg, WPARAM wParam, LPARAM lParam);
|
||||
static LRESULT __stdcall MenuSubClassProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam, UINT_PTR uIdSubclass, DWORD_PTR dwRefData);
|
||||
static void __stdcall WinEventProc(HWINEVENTHOOK hWinEventHook, DWORD dwEvent, HWND hWnd, LONG idObject, LONG idChild, DWORD idEventThread, DWORD dwmsEventTime);
|
||||
static LRESULT __stdcall KeyboardProc(int nCode, WPARAM wParam, LPARAM lParam);
|
||||
|
||||
inline static bool UnRegisterLayer()
|
||||
{
|
||||
return ::UnregisterClassW(WC_Shell_Window, Path::GetCurrentModule());
|
||||
//return DLL::User32<ATOM>("UnregisterClassW", WC_Shell_Window, Path::GetCurrentModule());
|
||||
}
|
||||
|
||||
inline static ATOM RegisterLayer()
|
||||
{
|
||||
WNDCLASSW wc_Layer{};
|
||||
wc_Layer.hInstance = Path::GetCurrentModule();
|
||||
wc_Layer.hbrBackground = static_cast<HBRUSH>(::GetStockObject(BLACK_BRUSH));
|
||||
//wc_Layer.hbrBackground = ::CreateSolidBrush(_theme.frame.background);// reinterpret_cast<HBRUSH>(NULL_BRUSH);
|
||||
wc_Layer.lpszClassName = WC_Shell_Window;
|
||||
wc_Layer.lpfnWndProc = LayerProc; /*::DefWindowProcW;*/
|
||||
return ::RegisterClassW(&wc_Layer);
|
||||
}
|
||||
|
||||
inline static ContextMenu *CreateAndInitialize(HWND hWnd, HMENU hMenu, Point const &pt, bool explorer, bool contextmenuhandler)
|
||||
{
|
||||
if(!Initializer::Status.Disabled)
|
||||
{
|
||||
auto ctx = new ContextMenu(hWnd, hMenu, pt);
|
||||
ctx->Selected.loader.explorer = explorer;
|
||||
ctx->Selected.loader.contextmenuhandler = contextmenuhandler;
|
||||
if(ctx->Initialize())
|
||||
return ctx;
|
||||
delete ctx;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
static bool is_swap_button()
|
||||
{
|
||||
/*
|
||||
auto fResult = GetSystemMetrics(SM_MOUSEPRESENT);
|
||||
if(fResult == 0)
|
||||
printf("No mouse installed.\n");
|
||||
else
|
||||
{
|
||||
printf("Mouse installed.\n");
|
||||
// Determine whether the buttons are swapped.
|
||||
fResult = GetSystemMetrics(SM_SWAPBUTTON);
|
||||
if(fResult == 0)
|
||||
printf("Buttons not swapped.\n");
|
||||
else printf("Buttons swapped.\n");
|
||||
}
|
||||
*/
|
||||
return Theme::SystemMetrics(SM_SWAPBUTTON, 0, true);
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,108 @@
|
||||
|
||||
#pragma once
|
||||
/*
|
||||
#include<string>
|
||||
#include<exception>
|
||||
#include <cstdarg>
|
||||
*/
|
||||
namespace Nilesoft
|
||||
{
|
||||
class Exception : public std::exception
|
||||
{
|
||||
protected:
|
||||
std::wstring msg{};
|
||||
|
||||
public:
|
||||
Exception(const std::string &message)
|
||||
: std::exception(message.c_str())
|
||||
{
|
||||
}
|
||||
|
||||
Exception(std::wstring const &message)
|
||||
: msg{ message }
|
||||
{
|
||||
}
|
||||
|
||||
Exception(const wchar_t *message)
|
||||
: msg{ message }
|
||||
{
|
||||
}
|
||||
|
||||
Exception(const wchar_t *format, ...)
|
||||
{
|
||||
if(format != nullptr)
|
||||
{
|
||||
va_list args;
|
||||
va_start(args, format);
|
||||
msg.resize(std::vswprintf(nullptr, 0, format, args), '\0');
|
||||
std::vswprintf(&msg[0], msg.size() + 1, format, args);
|
||||
va_end(args);
|
||||
}
|
||||
}
|
||||
|
||||
virtual std::wstring const &Message() const
|
||||
{
|
||||
return msg;
|
||||
}
|
||||
|
||||
static DWORD Filter(DWORD exceptionCode, EXCEPTION_POINTERS *ei)
|
||||
{
|
||||
(ei);
|
||||
// we handle all exceptions
|
||||
DWORD dwResult = EXCEPTION_EXECUTE_HANDLER;
|
||||
switch(exceptionCode)
|
||||
{
|
||||
case EXCEPTION_ACCESS_VIOLATION:
|
||||
case EXCEPTION_INVALID_HANDLE:
|
||||
case EXCEPTION_STACK_OVERFLOW:
|
||||
case EXCEPTION_ARRAY_BOUNDS_EXCEEDED:
|
||||
case EXCEPTION_BREAKPOINT:
|
||||
case EXCEPTION_DATATYPE_MISALIGNMENT:
|
||||
case EXCEPTION_FLT_DENORMAL_OPERAND:
|
||||
case EXCEPTION_FLT_DIVIDE_BY_ZERO:
|
||||
case EXCEPTION_FLT_INEXACT_RESULT:
|
||||
case EXCEPTION_FLT_INVALID_OPERATION:
|
||||
case EXCEPTION_FLT_OVERFLOW:
|
||||
case EXCEPTION_FLT_STACK_CHECK:
|
||||
case EXCEPTION_FLT_UNDERFLOW:
|
||||
case EXCEPTION_INT_DIVIDE_BY_ZERO:
|
||||
case EXCEPTION_INT_OVERFLOW:
|
||||
case EXCEPTION_PRIV_INSTRUCTION:
|
||||
case EXCEPTION_NONCONTINUABLE_EXCEPTION:
|
||||
case EXCEPTION_GUARD_PAGE:
|
||||
case EXCEPTION_INVALID_DISPOSITION:
|
||||
case EXCEPTION_ILLEGAL_INSTRUCTION:
|
||||
|
||||
case STATUS_HEAP_CORRUPTION:
|
||||
case STATUS_STACK_BUFFER_OVERRUN:
|
||||
{
|
||||
dwResult = EXCEPTION_EXECUTE_HANDLER;
|
||||
break;
|
||||
}
|
||||
}
|
||||
return dwResult;
|
||||
}
|
||||
|
||||
static DWORD Filter(DWORD exceptionCode)
|
||||
{
|
||||
return Filter(exceptionCode, nullptr);
|
||||
}
|
||||
};
|
||||
|
||||
/*class ParserException : public Exception
|
||||
{
|
||||
int _col;
|
||||
|
||||
public:
|
||||
ParserException(std::wstring const &message, int col)
|
||||
: Exception(message), _col(col)
|
||||
{
|
||||
}
|
||||
|
||||
ParserException(const wchar_t* message, int col)
|
||||
: Exception(message), _col(col)
|
||||
{
|
||||
}
|
||||
};*/
|
||||
}
|
||||
|
||||
@@ -0,0 +1,214 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
enum FSO : int32_t
|
||||
{
|
||||
FSO_TASKBAR,
|
||||
FSO_DESKTOP,
|
||||
FSO_DIRECTORY,
|
||||
FSO_FILE,
|
||||
FSO_DRIVE,
|
||||
FSO_NAMESPACE,
|
||||
|
||||
FSO_DRIVE_FIXED,
|
||||
FSO_DRIVE_VHD,
|
||||
FSO_DRIVE_USB,
|
||||
FSO_DRIVE_DVD,
|
||||
FSO_DRIVE_REMOVABLE,
|
||||
FSO_DRIVE_REMOTE,
|
||||
|
||||
FSO_NAMESPACE_COMPUTER,
|
||||
FSO_NAMESPACE_RECYCLEBIN,
|
||||
|
||||
FSO_BACK,
|
||||
FSO_BACK_DIRECTORY,
|
||||
FSO_BACK_NAMESPACE,
|
||||
FSO_BACK_NAMESPACE_COMPUTER,
|
||||
FSO_BACK_NAMESPACE_RECYCLEBIN,
|
||||
|
||||
FSO_BACK_DRIVE,
|
||||
FSO_BACK_DRIVE_FIXED,
|
||||
FSO_BACK_DRIVE_USB,
|
||||
FSO_BACK_DRIVE_VHD,
|
||||
FSO_BACK_DRIVE_DVD,
|
||||
FSO_BACK_DRIVE_REMOVABLE,
|
||||
FSO_BACK_DRIVE_REMOTE,
|
||||
|
||||
FSO_SIZE,
|
||||
FSO_COUNT,
|
||||
FSO_MAX
|
||||
};
|
||||
|
||||
struct FSO_TYPE
|
||||
{
|
||||
int32_t type;
|
||||
const wchar_t *name;
|
||||
};
|
||||
|
||||
const FSO_TYPE fs_types[FSO_SIZE] =
|
||||
{
|
||||
{FSO_TASKBAR,L"FSO_TASKBAR"},
|
||||
{FSO_DESKTOP,L"FSO_DESKTOP" },
|
||||
{FSO_DIRECTORY, L"FSO_DIRECTORY"},
|
||||
{FSO_FILE, L"FSO_FILE"},
|
||||
|
||||
{FSO_DRIVE, L"FSO_DRIVE"},
|
||||
{FSO_DRIVE_FIXED, L"FSO_DRIVE_FIXED"},
|
||||
{FSO_DRIVE_VHD,L"FSO_DRIVE_VHD" },
|
||||
{FSO_DRIVE_USB,L"FSO_DRIVE_USB"},
|
||||
{FSO_DRIVE_DVD,L"FSO_DRIVE_DVD"},
|
||||
{FSO_DRIVE_REMOVABLE,L"FSO_DRIVE_REMOVABLE"},
|
||||
{FSO_DRIVE_REMOTE,L"FSO_DRIVE_REMOTE"},
|
||||
|
||||
{FSO_NAMESPACE,L"FSO_NAMESPACE"},
|
||||
{FSO_NAMESPACE_COMPUTER,L"FSO_NAMESPACE_COMPUTER"},
|
||||
{FSO_NAMESPACE_RECYCLEBIN,L"FSO_NAMESPACE_RECYCLEBIN"},
|
||||
|
||||
{FSO_BACK,L"FSO_BACK"},
|
||||
{FSO_BACK_DIRECTORY,L"FSO_BACK_DIRECTORY"},
|
||||
{FSO_BACK_NAMESPACE,L"FSO_BACK_NAMESPACE"},
|
||||
{FSO_BACK_NAMESPACE_COMPUTER,L"FSO_BACK_NAMESPACE_COMPUTER"},
|
||||
{FSO_BACK_NAMESPACE_RECYCLEBIN,L"FSO_BACK_NAMESPACE_RECYCLEBIN"},
|
||||
|
||||
|
||||
{FSO_BACK_DRIVE,L"FSO_BACK_DRIVE"},
|
||||
{FSO_BACK_DRIVE_FIXED,L"FSO_BACK_DRIVE_FIXED"},
|
||||
{FSO_BACK_DRIVE_VHD,L"FSO_BACK_DRIVE_VHD"},
|
||||
{FSO_BACK_DRIVE_USB,L"FSO_BACK_DRIVE_USB"},
|
||||
{FSO_BACK_DRIVE_DVD,L"FSO_BACK_DRIVE_DVD"},
|
||||
{FSO_BACK_DRIVE_REMOVABLE,L"FSO_BACK_DRIVE_REMOVABLE"},
|
||||
{FSO_BACK_DRIVE_REMOTE,L"FSO_BACK_DRIVE_REMOTE"}
|
||||
};
|
||||
|
||||
|
||||
//FileSystemObject
|
||||
class FileSystemObjects
|
||||
{
|
||||
public:
|
||||
int32_t Types[FSO_MAX]{ FALSE };
|
||||
int32_t count = FSO_SIZE;
|
||||
int32_t exclude = 0;
|
||||
|
||||
static constexpr int32_t EXCLUDE = -1;
|
||||
|
||||
public:
|
||||
FileSystemObjects() noexcept
|
||||
{
|
||||
}
|
||||
|
||||
FileSystemObjects(BOOL all)
|
||||
{
|
||||
this->set(all);
|
||||
}
|
||||
|
||||
~FileSystemObjects()
|
||||
{
|
||||
}
|
||||
|
||||
FileSystemObjects &operator=(FileSystemObjects const &fso)
|
||||
{
|
||||
count = fso.count;
|
||||
exclude = fso.exclude;
|
||||
::memcpy(&Types, fso.Types, sizeof(Types));
|
||||
//for(int32_t i = 0; i < FSO_MAX; i++) Types[i] = fso.Types[i];
|
||||
return *this;
|
||||
}
|
||||
|
||||
void set(BOOL all = TRUE)
|
||||
{
|
||||
count = FSO_SIZE - 1;
|
||||
::memset(&Types, all, sizeof(Types));
|
||||
}
|
||||
|
||||
bool excluded(int32_t t) const
|
||||
{
|
||||
return Types[t] == EXCLUDE;
|
||||
}
|
||||
|
||||
bool excluded(std::initializer_list<uint32_t> list) const
|
||||
{
|
||||
for(auto t : list)
|
||||
{
|
||||
if(Types[t] == EXCLUDE)
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool assgined(uint32_t t) const { return Types[t] > 0; }
|
||||
|
||||
bool assgined(std::initializer_list<uint32_t> types) const
|
||||
{
|
||||
int32_t ret = 0;
|
||||
for(auto t : types) if(assgined(t)) ret++;
|
||||
return ret > 0;
|
||||
}
|
||||
|
||||
bool is_all() const
|
||||
{
|
||||
for(int32_t t = 0; t < FSO_SIZE; t++)
|
||||
if(!assgined(t)) return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
bool is_taskbar() const { return assgined(FSO_TASKBAR); }
|
||||
bool is_desktop() const { return assgined(FSO_DESKTOP); }
|
||||
//is background
|
||||
bool is_back() const
|
||||
{
|
||||
return assgined({
|
||||
FSO_BACK,
|
||||
FSO_BACK_DIRECTORY,
|
||||
FSO_BACK_DRIVE, FSO_BACK_DRIVE_FIXED, FSO_BACK_DRIVE_VHD, FSO_BACK_DRIVE_USB, FSO_BACK_DRIVE_DVD, FSO_BACK_DRIVE_REMOVABLE,
|
||||
FSO_BACK_NAMESPACE,FSO_BACK_NAMESPACE, FSO_BACK_NAMESPACE_COMPUTER, FSO_BACK_NAMESPACE_RECYCLEBIN
|
||||
});
|
||||
}
|
||||
|
||||
bool is_file() const { return assgined(FSO_FILE); }
|
||||
bool is_directory() const { return assgined(FSO_DIRECTORY); }
|
||||
|
||||
bool is_drives() const
|
||||
{
|
||||
return assgined({ FSO_DRIVE,FSO_DRIVE_FIXED,FSO_DRIVE_USB,
|
||||
FSO_DRIVE_DVD,FSO_DRIVE_REMOVABLE });
|
||||
}
|
||||
|
||||
bool is_namespaces() const
|
||||
{
|
||||
return assgined({
|
||||
FSO_NAMESPACE,
|
||||
FSO_NAMESPACE_COMPUTER,
|
||||
FSO_NAMESPACE_RECYCLEBIN,
|
||||
FSO_BACK_NAMESPACE,
|
||||
FSO_BACK_NAMESPACE_COMPUTER,
|
||||
FSO_BACK_NAMESPACE_RECYCLEBIN
|
||||
});
|
||||
}
|
||||
|
||||
static bool is_type_back(uint32_t id)
|
||||
{
|
||||
switch(id)
|
||||
{
|
||||
case IDENT_TYPE_D:
|
||||
case IDENT_TYPE_DIR:
|
||||
case IDENT_TYPE_DIRECTORY:
|
||||
case IDENT_TYPE_R:
|
||||
case IDENT_TYPE_ROOT:
|
||||
case IDENT_TYPE_DRIVE:
|
||||
case IDENT_TYPE_FIXED:
|
||||
case IDENT_TYPE_USB:
|
||||
case IDENT_TYPE_VHD:
|
||||
case IDENT_TYPE_DVD:
|
||||
case IDENT_TYPE_REMOVABLE:
|
||||
case IDENT_TYPE_NS:
|
||||
case IDENT_TYPE_NAMESPACE:
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,266 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
class FindPattern
|
||||
{
|
||||
public:
|
||||
enum class SearchType
|
||||
{
|
||||
None,
|
||||
Title,
|
||||
Extension,
|
||||
Path,
|
||||
Not,
|
||||
Start,
|
||||
End,
|
||||
Equals,
|
||||
Contains,
|
||||
Any
|
||||
};
|
||||
|
||||
struct Pattern
|
||||
{
|
||||
std::wstring value;
|
||||
bool Not = 0;
|
||||
SearchType search = SearchType::Title;
|
||||
SearchType Pos = SearchType::Contains;
|
||||
|
||||
Pattern() = default;
|
||||
Pattern(Pattern &&other) = default;
|
||||
Pattern(const wchar_t *src, const size_t length)
|
||||
{
|
||||
std::wstring_view s(src, length);
|
||||
/*
|
||||
!*text title not end
|
||||
.!*text ext not end
|
||||
:!*text path not end
|
||||
:!*text*
|
||||
text*!:
|
||||
*/
|
||||
|
||||
if(!s.empty())
|
||||
{
|
||||
if(s.length() == 1 && s.front() == '*')
|
||||
{
|
||||
Pos = SearchType::Any;
|
||||
}
|
||||
else
|
||||
{
|
||||
bool found = false;
|
||||
|
||||
if(s.front() == '.' || s.front() == ':')
|
||||
{
|
||||
search = s.front() == '.' ? SearchType::Extension : SearchType::Path;
|
||||
s.remove_prefix(1);
|
||||
}
|
||||
|
||||
if(s.front() == '!' || s.front() == '*' || s.front() == '"')
|
||||
{
|
||||
if(s.front() == '!')
|
||||
{
|
||||
s.remove_prefix(1);
|
||||
Not = true;
|
||||
}
|
||||
|
||||
if(s.front() == '*')
|
||||
{
|
||||
s.remove_prefix(1);
|
||||
if(s.back() == '*')
|
||||
{
|
||||
s.remove_suffix(1);
|
||||
Pos = SearchType::Contains;
|
||||
}
|
||||
else
|
||||
{
|
||||
Pos = SearchType::End;
|
||||
}
|
||||
found = true;
|
||||
}
|
||||
else if(s.length() > 2u && s.front() == '"' && s.back() == '"')
|
||||
{
|
||||
s.remove_prefix(1);
|
||||
s.remove_suffix(1);
|
||||
Pos = SearchType::Equals;
|
||||
found = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
Pos = SearchType::Contains;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if(s.back() == '.' || s.back() == ':')
|
||||
{
|
||||
search = s.back() == '.' ? SearchType::Extension : SearchType::Path;
|
||||
s.remove_suffix(1);
|
||||
}
|
||||
|
||||
if(s.back() == '!' || s.back() == '*')
|
||||
{
|
||||
if(s.back() == '!')
|
||||
{
|
||||
s.remove_suffix(1);
|
||||
Not = true;
|
||||
}
|
||||
|
||||
if(s.back() == '*')
|
||||
{
|
||||
s.remove_suffix(1);
|
||||
if(s.front() == '*')
|
||||
{
|
||||
s.remove_prefix(1);
|
||||
Pos = SearchType::Contains;
|
||||
}
|
||||
else
|
||||
{
|
||||
Pos = SearchType::Start;
|
||||
}
|
||||
found = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if(!s.empty() && (found || search != SearchType::Title))
|
||||
{
|
||||
value = s;
|
||||
return;
|
||||
}
|
||||
|
||||
Pos = SearchType::Contains;
|
||||
Not = false;
|
||||
}
|
||||
|
||||
value = src;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
public:
|
||||
std::vector<Pattern> matches;
|
||||
|
||||
FindPattern() = default;
|
||||
FindPattern(FindPattern &&other) = default;
|
||||
|
||||
bool find(Pattern const &pat, string const *title, string const *ext = nullptr, string const *path = nullptr) const
|
||||
{
|
||||
bool ret = false;
|
||||
switch(pat.Pos)
|
||||
{
|
||||
case SearchType::Any:
|
||||
return true;
|
||||
case SearchType::Start:
|
||||
{
|
||||
if(ext && pat.search == SearchType::Extension)
|
||||
ret = ext->starts_with(pat.value);
|
||||
else if(path && pat.search == SearchType::Path)
|
||||
ret = path->starts_with(pat.value);
|
||||
else if(title)
|
||||
ret = title->starts_with(pat.value);
|
||||
break;
|
||||
}
|
||||
case SearchType::End:
|
||||
{
|
||||
if(ext && pat.search == SearchType::Extension)
|
||||
ret = ext->ends_with(pat.value);
|
||||
else if(path && pat.search == SearchType::Path)
|
||||
ret = path->ends_with(pat.value);
|
||||
else if(title)
|
||||
ret = title->ends_with(pat.value);
|
||||
break;
|
||||
}
|
||||
case SearchType::Equals:
|
||||
{
|
||||
if(ext && pat.search == SearchType::Extension)
|
||||
ret = ext->equals(pat.value);
|
||||
else if(path && pat.search == SearchType::Path)
|
||||
ret = path->equals(pat.value);
|
||||
else if(title)
|
||||
ret = title->equals(pat.value);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
{
|
||||
if(ext && pat.search == SearchType::Extension)
|
||||
ret = ext->contains(pat.value.c_str());
|
||||
else if(path && pat.search == SearchType::Path)
|
||||
ret = path->contains(pat.value.c_str());
|
||||
else if(title)
|
||||
ret = title->contains(pat.value.c_str());
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if(pat.Not)
|
||||
{
|
||||
if(ret) return false;
|
||||
ret = true; // inc finder
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
bool find(string const *title, string const *ext = nullptr, string const *path = nullptr) const
|
||||
{
|
||||
uint32_t ret = 0;
|
||||
for(auto const &pat : matches)
|
||||
ret += find(pat, title, ext, path);
|
||||
return ret > 0;
|
||||
}
|
||||
|
||||
bool split(wchar_t const *text, wchar_t seperator)
|
||||
{
|
||||
if(!text || *text == 0) return false;
|
||||
|
||||
auto str = text;
|
||||
string value;
|
||||
size_t count = 0;
|
||||
while(*str != 0) count += (*str++ == seperator);
|
||||
matches.reserve(count);
|
||||
str = text;
|
||||
while(*str != 0)
|
||||
{
|
||||
if(seperator == *str)
|
||||
{
|
||||
if(!value.trim().empty())
|
||||
matches.emplace_back(value.c_str(), value.length());
|
||||
value = nullptr;
|
||||
}
|
||||
else value.append(*str);
|
||||
str++;
|
||||
};
|
||||
|
||||
if(!value.trim().empty())
|
||||
matches.emplace_back(value.c_str(), value.length());
|
||||
|
||||
return !matches.empty();
|
||||
}
|
||||
|
||||
bool operator()(string const &text, wchar_t seperator)
|
||||
{
|
||||
return split(text, seperator);
|
||||
}
|
||||
|
||||
bool operator()(string const *title) const
|
||||
{
|
||||
return find(title, nullptr, nullptr);
|
||||
}
|
||||
|
||||
bool operator()(string const *title, string const *ext, string const *path) const
|
||||
{
|
||||
return find(title, ext, path);
|
||||
}
|
||||
|
||||
bool empty() const noexcept { return matches.empty(); }
|
||||
size_t size() const noexcept { return matches.size(); }
|
||||
|
||||
const auto begin()const noexcept { return matches.begin(); }
|
||||
const auto end()const noexcept { return matches.end(); }
|
||||
auto begin() { return matches.begin(); }
|
||||
auto end() { return matches.end(); }
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,801 @@
|
||||
#pragma once
|
||||
|
||||
/*
|
||||
#ifndef LIBVALINET_HOOKING_IATPATCH_H_
|
||||
#define LIBVALINET_HOOKING_IATPATCH_H_
|
||||
#include <Windows.h>
|
||||
#include <DbgHelp.h>
|
||||
#ifdef _LIBVALINET_DEBUG_HOOKING_IATPATCH
|
||||
#include <stdio.h>
|
||||
#include <conio.h>
|
||||
#endif
|
||||
// https://blog.neteril.org/blog/2016/12/23/diverting-functions-windows-iat-patching/
|
||||
inline BOOL VnPatchIAT(HMODULE hMod, PSTR libName, PSTR funcName, uintptr_t hookAddr)
|
||||
{
|
||||
// Increment module reference count to prevent other threads from unloading it while we're working with it
|
||||
HMODULE module;
|
||||
if (!GetModuleHandleExW(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS, hMod, &module)) return FALSE;
|
||||
|
||||
// Get a reference to the import table to locate the kernel32 entry
|
||||
ULONG size;
|
||||
PIMAGE_IMPORT_DESCRIPTOR importDescriptor = (PIMAGE_IMPORT_DESCRIPTOR)ImageDirectoryEntryToDataEx(module, TRUE, IMAGE_DIRECTORY_ENTRY_IMPORT, &size, NULL);
|
||||
|
||||
// In the import table find the entry that corresponds to kernel32
|
||||
BOOL found = FALSE;
|
||||
while (importDescriptor->Characteristics && importDescriptor->Name) {
|
||||
PSTR importName = (PSTR)((PBYTE)module + importDescriptor->Name);
|
||||
if (_stricmp(importName, libName) == 0) {
|
||||
#ifdef _LIBVALINET_DEBUG_HOOKING_IATPATCH
|
||||
printf("[PatchIAT] Found %s in IAT.\n", libName);
|
||||
#endif
|
||||
found = TRUE;
|
||||
break;
|
||||
}
|
||||
importDescriptor++;
|
||||
}
|
||||
if (!found) {
|
||||
FreeLibrary(module);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// From the kernel32 import descriptor, go over its IAT thunks to
|
||||
// find the one used by the rest of the code to call GetProcAddress
|
||||
PIMAGE_THUNK_DATA oldthunk = (PIMAGE_THUNK_DATA)((PBYTE)module + importDescriptor->OriginalFirstThunk);
|
||||
PIMAGE_THUNK_DATA thunk = (PIMAGE_THUNK_DATA)((PBYTE)module + importDescriptor->FirstThunk);
|
||||
while (thunk->u1.Function) {
|
||||
PROC* funcStorage = (PROC*)&thunk->u1.Function;
|
||||
|
||||
BOOL bFound = FALSE;
|
||||
if (oldthunk->u1.Ordinal & IMAGE_ORDINAL_FLAG)
|
||||
{
|
||||
bFound = (!(*((WORD*)&(funcName)+1)) && IMAGE_ORDINAL32(oldthunk->u1.Ordinal) == (DWORD)funcName);
|
||||
}
|
||||
else
|
||||
{
|
||||
PIMAGE_IMPORT_BY_NAME byName = (PIMAGE_IMPORT_BY_NAME)((uintptr_t)module + oldthunk->u1.AddressOfData);
|
||||
bFound = ((*((WORD*)&(funcName)+1)) && !_stricmp((char*)byName->Name, funcName));
|
||||
}
|
||||
|
||||
// Found it, now let's patch it
|
||||
if (bFound) {
|
||||
// Get the memory page where the info is stored
|
||||
MEMORY_BASIC_INFORMATION mbi;
|
||||
VirtualQuery(funcStorage, &mbi, sizeof(MEMORY_BASIC_INFORMATION));
|
||||
|
||||
// Try to change the page to be writable if it's not already
|
||||
if (!VirtualProtect(mbi.BaseAddress, mbi.RegionSize, PAGE_READWRITE, &mbi.Protect)) {
|
||||
FreeLibrary(module);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// Store our hook
|
||||
*funcStorage = (PROC)hookAddr;
|
||||
#ifdef _LIBVALINET_DEBUG_HOOKING_IATPATCH
|
||||
if ((*((WORD*)&(funcName)+1)))
|
||||
{
|
||||
printf("[PatchIAT] Patched %s in %s to 0x%p.\n", funcName, libName, hookAddr);
|
||||
}
|
||||
else
|
||||
{
|
||||
printf("[PatchIAT] Patched 0x%x in %s to 0x%p.\n", funcName, libName, hookAddr);
|
||||
}
|
||||
#endif
|
||||
|
||||
// Restore the old flag on the page
|
||||
DWORD dwOldProtect;
|
||||
VirtualProtect(mbi.BaseAddress, mbi.RegionSize, mbi.Protect, &dwOldProtect);
|
||||
|
||||
// Profit
|
||||
FreeLibrary(module);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
thunk++;
|
||||
oldthunk++;
|
||||
}
|
||||
|
||||
FreeLibrary(module);
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
// https://stackoverflow.com/questions/50973053/how-to-hook-delay-imports
|
||||
inline BOOL VnPatchDelayIAT(HMODULE hMod, PSTR libName, PSTR funcName, uintptr_t hookAddr)
|
||||
{
|
||||
// Increment module reference count to prevent other threads from unloading it while we're working with it
|
||||
HMODULE lib;
|
||||
if (!GetModuleHandleExW(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS, hMod, &lib)) return FALSE;
|
||||
|
||||
PIMAGE_DOS_HEADER dos = (PIMAGE_DOS_HEADER)lib;
|
||||
PIMAGE_NT_HEADERS nt = (PIMAGE_NT_HEADERS)((uintptr_t)lib + dos->e_lfanew);
|
||||
PIMAGE_DELAYLOAD_DESCRIPTOR dload = (PIMAGE_DELAYLOAD_DESCRIPTOR)((uintptr_t)lib +
|
||||
nt->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_DELAY_IMPORT].VirtualAddress);
|
||||
while (dload->DllNameRVA)
|
||||
{
|
||||
char* dll = (char*)((uintptr_t)lib + dload->DllNameRVA);
|
||||
if (!_stricmp(dll, libName)) {
|
||||
#ifdef _LIBVALINET_DEBUG_HOOKING_IATPATCH
|
||||
printf("[PatchDelayIAT] Found %s in IAT.\n", libName);
|
||||
#endif
|
||||
|
||||
PIMAGE_THUNK_DATA firstthunk = (PIMAGE_THUNK_DATA)((uintptr_t)lib + dload->ImportNameTableRVA);
|
||||
PIMAGE_THUNK_DATA functhunk = (PIMAGE_THUNK_DATA)((uintptr_t)lib + dload->ImportAddressTableRVA);
|
||||
while (firstthunk->u1.AddressOfData)
|
||||
{
|
||||
if (firstthunk->u1.Ordinal & IMAGE_ORDINAL_FLAG)
|
||||
{
|
||||
if (!(*((WORD*)&(funcName)+1)) && IMAGE_ORDINAL32(firstthunk->u1.Ordinal) == (DWORD)funcName)
|
||||
{
|
||||
DWORD oldProtect;
|
||||
if (VirtualProtect(&functhunk->u1.Function, sizeof(uintptr_t), PAGE_EXECUTE_READWRITE, &oldProtect))
|
||||
{
|
||||
functhunk->u1.Function = (uintptr_t)hookAddr;
|
||||
VirtualProtect(&functhunk->u1.Function, sizeof(uintptr_t), oldProtect, &oldProtect);
|
||||
#ifdef _LIBVALINET_DEBUG_HOOKING_IATPATCH
|
||||
printf("[PatchDelayIAT] Patched 0x%x in %s to 0x%p.\n", funcName, libName, hookAddr);
|
||||
#endif
|
||||
FreeLibrary(lib);
|
||||
return TRUE;
|
||||
}
|
||||
FreeLibrary(lib);
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
PIMAGE_IMPORT_BY_NAME byName = (PIMAGE_IMPORT_BY_NAME)((uintptr_t)lib + firstthunk->u1.AddressOfData);
|
||||
if ((*((WORD*)&(funcName)+1)) && !_stricmp((char*)byName->Name, funcName))
|
||||
{
|
||||
DWORD oldProtect;
|
||||
if (VirtualProtect(&functhunk->u1.Function, sizeof(uintptr_t), PAGE_EXECUTE_READWRITE, &oldProtect))
|
||||
{
|
||||
functhunk->u1.Function = (uintptr_t)hookAddr;
|
||||
VirtualProtect(&functhunk->u1.Function, sizeof(uintptr_t), oldProtect, &oldProtect);
|
||||
#ifdef _LIBVALINET_DEBUG_HOOKING_IATPATCH
|
||||
printf("[PatchDelayIAT] Patched %s in %s to 0x%p.\n", funcName, libName, hookAddr);
|
||||
#endif
|
||||
FreeLibrary(lib);
|
||||
return TRUE;
|
||||
}
|
||||
FreeLibrary(lib);
|
||||
return FALSE;
|
||||
}
|
||||
}
|
||||
functhunk++;
|
||||
firstthunk++;
|
||||
}
|
||||
}
|
||||
dload++;
|
||||
}
|
||||
FreeLibrary(lib);
|
||||
return FALSE;
|
||||
}
|
||||
#endif
|
||||
*/
|
||||
namespace Nilesoft::Shell
|
||||
{
|
||||
struct IATHook
|
||||
{
|
||||
HMODULE _hModule{};
|
||||
std::string _import{};
|
||||
uintptr_t _orignal{};
|
||||
uintptr_t _detour{}; // trampoline
|
||||
IMAGE_THUNK_DATA *_thunk{};
|
||||
|
||||
IATHook() {}
|
||||
|
||||
IATHook(HMODULE hModule, const char *import = nullptr, void *orignal = nullptr, void *detour = nullptr)
|
||||
{
|
||||
init(hModule, import, orignal, detour);
|
||||
}
|
||||
|
||||
IATHook(const wchar_t *mdule, const char *import = nullptr, void *orignal = nullptr, void *detour = nullptr)
|
||||
{
|
||||
init(mdule, import, orignal, detour);
|
||||
}
|
||||
|
||||
IATHook(IATHook &&other) noexcept
|
||||
{
|
||||
_hModule = std::exchange(other._hModule, nullptr);
|
||||
_import = std::move(other._import);
|
||||
_orignal = std::exchange(other._orignal, 0);
|
||||
_detour = std::exchange(other._detour, 0);
|
||||
_thunk = std::exchange(other._thunk, nullptr);
|
||||
}
|
||||
|
||||
~IATHook()
|
||||
{
|
||||
uninstall(true);
|
||||
// free when use GetModuleHandleExW
|
||||
if(_hModule) ::FreeLibrary(_hModule);
|
||||
}
|
||||
|
||||
IATHook &init(HMODULE hModule, const char *import, void *orignal, void *detour)
|
||||
{
|
||||
// Increment module reference count to prevent other threads from unloading it while we're working with it
|
||||
if(::GetModuleHandleExW(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS, (LPCWSTR)hModule, &_hModule) && _hModule)
|
||||
{
|
||||
//_hModule = hModule;
|
||||
_import = import;
|
||||
_orignal = reinterpret_cast<uintptr_t>(orignal);
|
||||
_detour = reinterpret_cast<uintptr_t>(detour);
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
IATHook &init(const wchar_t *mdule, const char *import, void *orignal, void *detour)
|
||||
{
|
||||
return init(::GetModuleHandleW(mdule), import, orignal, detour);
|
||||
}
|
||||
|
||||
IATHook &init(const wchar_t *mdule, const char *import, const char *orignal, void *detour)
|
||||
{
|
||||
if(auto h = ::GetModuleHandleA(import); h)
|
||||
{
|
||||
return init(::GetModuleHandleW(mdule), import, static_cast<void *>(::GetProcAddress(h, orignal)), detour);
|
||||
}
|
||||
return *this;
|
||||
}
|
||||
|
||||
//attach
|
||||
bool install(bool flush = true)
|
||||
{
|
||||
if(installed())
|
||||
return true;
|
||||
return get_thunk() && commit(_detour, flush);
|
||||
}
|
||||
|
||||
//detach
|
||||
bool uninstall(bool cleare = false, bool flush = true)
|
||||
{
|
||||
auto ret = false;
|
||||
|
||||
if(installed())
|
||||
ret = commit(_orignal, flush);
|
||||
|
||||
if(cleare)
|
||||
{
|
||||
_hModule = {};
|
||||
_import = {};
|
||||
_orignal = {};
|
||||
_detour = {};
|
||||
_thunk = {};
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
bool installed() const
|
||||
{
|
||||
return _thunk &&_thunk->u1.Function == _detour;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
T orignal() { return static_cast<T>(_orignal); }
|
||||
|
||||
/*template <typename T, typename... Args>
|
||||
auto invoke(Args&&... args)
|
||||
{
|
||||
if(_orignal && _installed)
|
||||
return reinterpret_cast<T*>(_orignal)(args...);
|
||||
return reinterpret_cast<T *>(T);
|
||||
}*/
|
||||
|
||||
template <typename T, typename... Args>
|
||||
auto invoke(Args&&... args)
|
||||
{
|
||||
return reinterpret_cast<T *>(_orignal)(args...);
|
||||
}
|
||||
|
||||
private:
|
||||
|
||||
template<typename T, typename O = DWORD>
|
||||
static inline T *Ptr(LPVOID base, O rva = 0)
|
||||
{
|
||||
return reinterpret_cast<T *>(reinterpret_cast<uint8_t *>(base) + rva);
|
||||
}
|
||||
|
||||
bool commit(uintptr_t lpfunc, bool flush = true)
|
||||
{
|
||||
if(_thunk && lpfunc) __try
|
||||
{
|
||||
if(lpfunc == _thunk->u1.Function)
|
||||
return true;
|
||||
|
||||
DWORD protect;
|
||||
if(::VirtualProtect(&_thunk->u1.Function, sizeof(uintptr_t), PAGE_EXECUTE_READWRITE, &protect))
|
||||
{
|
||||
_thunk->u1.Function = lpfunc;
|
||||
if(::VirtualProtect(&_thunk->u1.Function, sizeof(uintptr_t), protect, &protect))
|
||||
{
|
||||
if(flush)
|
||||
{
|
||||
//https://devblogs.microsoft.com/oldnewthing/20190902-00/?p=102828
|
||||
::FlushInstructionCache(::GetCurrentProcess(), &_thunk->u1.Function, sizeof(ULONG_PTR));
|
||||
}
|
||||
return true;
|
||||
}
|
||||
}
|
||||
} except {}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool get_thunk()
|
||||
{
|
||||
if(_thunk) return true;
|
||||
|
||||
if(!_hModule || _import.empty() || !_orignal)
|
||||
return false;
|
||||
|
||||
// Query to get existing execute access.
|
||||
//MEMORY_BASIC_INFORMATION mbi{};
|
||||
//if(::VirtualQuery(lpfunc, &mbi, sizeof(mbi)) == 0)
|
||||
// return false;
|
||||
__try
|
||||
{
|
||||
auto dos = Ptr<IMAGE_DOS_HEADER>(_hModule);
|
||||
|
||||
if(!dos || (dos->e_magic != IMAGE_DOS_SIGNATURE))
|
||||
return false;
|
||||
|
||||
auto nt = Ptr<IMAGE_NT_HEADERS>(dos, dos->e_lfanew);
|
||||
if(!nt || (nt->Signature != IMAGE_NT_SIGNATURE))
|
||||
return false;
|
||||
|
||||
auto va = nt->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
|
||||
auto id = Ptr<IMAGE_IMPORT_DESCRIPTOR>(dos, va);
|
||||
|
||||
//IMAGE_DELAYLOAD_DESCRIPTOR
|
||||
|
||||
if(!va || !id) return false;
|
||||
|
||||
// Get a reference to the import table to locate the DLL entry
|
||||
for(uint32_t i = 0; id[i].Characteristics && id[i].FirstThunk; i++) __try
|
||||
{
|
||||
auto dll_import = Ptr<char>(dos, id[i].Name);
|
||||
if(::_stricmp(dll_import, _import.c_str())) //memicmp
|
||||
continue;
|
||||
for(auto ftd = Ptr<IMAGE_THUNK_DATA>(dos, id[i].FirstThunk); ftd->u1.Function; ftd++) __try
|
||||
{
|
||||
if(_orignal == ftd->u1.Function)
|
||||
{
|
||||
_thunk = ftd;
|
||||
return true;
|
||||
}
|
||||
} except { return false; }
|
||||
} except { return false; }
|
||||
} except { return false; }
|
||||
return false;
|
||||
}
|
||||
|
||||
bool get_delay_thunk()
|
||||
{
|
||||
if(_thunk) return true;
|
||||
|
||||
if(!_hModule || _import.empty() || !_orignal)
|
||||
return false;
|
||||
|
||||
// Query to get existing execute access.
|
||||
//MEMORY_BASIC_INFORMATION mbi{};
|
||||
//if(::VirtualQuery(lpfunc, &mbi, sizeof(mbi)) == 0)
|
||||
// return false;
|
||||
__try
|
||||
{
|
||||
auto dos = Ptr<IMAGE_DOS_HEADER>(_hModule);
|
||||
|
||||
if(!dos || (dos->e_magic != IMAGE_DOS_SIGNATURE))
|
||||
return false;
|
||||
|
||||
auto nt = Ptr<IMAGE_NT_HEADERS>(dos, dos->e_lfanew);
|
||||
if(!nt || (nt->Signature != IMAGE_NT_SIGNATURE))
|
||||
return false;
|
||||
|
||||
auto va = nt->OptionalHeader.DataDirectory[IMAGE_DIRECTORY_ENTRY_IMPORT].VirtualAddress;
|
||||
auto dl = Ptr<IMAGE_DELAYLOAD_DESCRIPTOR>(dos, va);
|
||||
|
||||
if(!va || !dl) return false;
|
||||
|
||||
while(dl->DllNameRVA)
|
||||
{
|
||||
auto dll_import = Ptr<char>(dos,dl->DllNameRVA);
|
||||
if(0 == ::_stricmp(dll_import, _import.c_str())) //memicmp
|
||||
{
|
||||
auto firstthunk = Ptr<IMAGE_THUNK_DATA>(dos, dl->ImportNameTableRVA);
|
||||
auto functhunk = Ptr<IMAGE_THUNK_DATA>(dos, dl->ImportAddressTableRVA);
|
||||
while(firstthunk->u1.AddressOfData)
|
||||
{
|
||||
if(firstthunk->u1.Function == _orignal)
|
||||
{
|
||||
_thunk = functhunk;
|
||||
return true;
|
||||
}
|
||||
|
||||
/*if(firstthunk->u1.Ordinal & IMAGE_ORDINAL_FLAG)
|
||||
{
|
||||
if(!(*((WORD *)&(funcName)+1)) && IMAGE_ORDINAL32(firstthunk->u1.Ordinal) == (DWORD)funcName)
|
||||
{
|
||||
_thunk = functhunk;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
auto byName = Ptr<IMAGE_IMPORT_BY_NAME>(dos, firstthunk->u1.AddressOfData);
|
||||
if((*((WORD *)&(funcName)+1)) && !_stricmp((char *)byName->Name, funcName))
|
||||
{
|
||||
_thunk = functhunk;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
*/
|
||||
functhunk++;
|
||||
firstthunk++;
|
||||
}
|
||||
}
|
||||
dl++;
|
||||
}
|
||||
} except{ return false; }
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
/*
|
||||
class InlineHook
|
||||
{
|
||||
#ifdef _WIN64
|
||||
static constexpr int size = 12;
|
||||
#else
|
||||
static constexpr int size = 6;
|
||||
#endif
|
||||
|
||||
uint8_t *_addr{};
|
||||
uint8_t _detour[size]{};
|
||||
uint8_t _orignal[size]{};
|
||||
unsigned long protect{};
|
||||
|
||||
public:
|
||||
HMODULE _hModule{};
|
||||
|
||||
InlineHook()
|
||||
{
|
||||
}
|
||||
|
||||
~InlineHook()
|
||||
{
|
||||
destroy();
|
||||
}
|
||||
|
||||
void destroy()
|
||||
{
|
||||
unhook();
|
||||
}
|
||||
|
||||
operator bool() const { return is_hooked(); }
|
||||
|
||||
bool is_hooked() const
|
||||
{
|
||||
return _addr && _detour && ::memcmp(_addr, _detour, size);
|
||||
}
|
||||
|
||||
bool create(const wchar_t *module, const char *func, void *dst)
|
||||
{
|
||||
if(auto hModule = ::GetModuleHandleW(module); hModule)
|
||||
return create(hModule, ::GetProcAddress(hModule, func), dst);
|
||||
return false;
|
||||
}
|
||||
|
||||
bool create(HMODULE hModule, const char *func, void *dst)
|
||||
{
|
||||
return create(hModule, ::GetProcAddress(hModule, func), dst);
|
||||
}
|
||||
|
||||
bool create(HMODULE hModule, void *func, void *dst)
|
||||
{
|
||||
_hModule = hModule;
|
||||
return create(func, dst);
|
||||
}
|
||||
|
||||
bool create(void *orignal, void *detour)
|
||||
{
|
||||
if(is_hooked())
|
||||
return true;
|
||||
|
||||
if(!orignal || !detour)
|
||||
return false;
|
||||
|
||||
_addr = reinterpret_cast<uint8_t *>(orignal);
|
||||
|
||||
::memcpy(_orignal, orignal, size);
|
||||
|
||||
#ifdef _WIN64
|
||||
_detour[0] = 0x48;
|
||||
_detour[1] = 0xB8;
|
||||
::memcpy(_detour + 2, &detour, sizeof(uintptr_t));
|
||||
_detour[10] = 0x50;
|
||||
_detour[11] = 0xC3;
|
||||
#else
|
||||
_detour[0] = 0xE9; // jmp
|
||||
auto offset = uint32_t(detour) - uint32_t(orignal) - 5;
|
||||
::memcpy(_detour + 1, &offset, sizeof(uint32_t));
|
||||
_detour[5] = 0xC3; // ret
|
||||
#endif
|
||||
return hook();
|
||||
}
|
||||
|
||||
bool hook() { return commit(_detour); }
|
||||
bool unhook() { return commit(_orignal); }
|
||||
|
||||
bool commit(void *lpfunc)
|
||||
{
|
||||
if(lpfunc && _addr)
|
||||
{
|
||||
if(::memcmp(_addr, lpfunc, size) == 0)
|
||||
return true;
|
||||
if(::VirtualProtect(_addr, size, PAGE_EXECUTE_READWRITE, &protect))
|
||||
{
|
||||
::memcpy(_addr, lpfunc, size);
|
||||
::VirtualProtect(_addr, size, protect, &protect);
|
||||
// Clear CPU instruction cache
|
||||
::FlushInstructionCache(::GetCurrentProcess(), _addr, size);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
//using fnDllGetClassObjectProc = HRESULT(__stdcall *)(REFCLSID rclsid, _In_ REFIID riid, LPVOID *ppv);
|
||||
|
||||
//HRESULT __stdcall invoke(REFCLSID rclsid, _In_ REFIID riid, LPVOID *ppv)
|
||||
//{
|
||||
// if(::VirtualProtect(addr, size, PAGE_EXECUTE_READWRITE, &protect))
|
||||
// {
|
||||
// ::memcpy(addr, orig, sizeof(orig));
|
||||
// auto call = (fnDllGetClassObjectProc)(addr);
|
||||
// return call(rclsid, riid, ppv);
|
||||
// ::memcpy(addr, jmp, sizeof(jmp));
|
||||
// ::VirtualProtect(addr, size, protect, &protect);
|
||||
// }
|
||||
// return CLASS_E_CLASSNOTAVAILABLE;
|
||||
//}
|
||||
//
|
||||
//
|
||||
//template <typename T, typename... Args>
|
||||
//auto invoke2(Args&&... args)
|
||||
//{
|
||||
// T *res{};
|
||||
// if(::VirtualProtect(addr, size, PAGE_EXECUTE_READWRITE, &protect))
|
||||
// {
|
||||
// ::memcpy(addr, orig, sizeof(orig));
|
||||
// res = (T*)(addr)(args...);
|
||||
// ::memcpy(addr, jmp, sizeof(jmp));
|
||||
// ::VirtualProtect(addr, size, protect, &protect);
|
||||
// }
|
||||
// return res;
|
||||
//}
|
||||
|
||||
void *orignal() const { uint8_t a[12]{}; return ::memcpy(a, _orignal, sizeof(_orignal)); }
|
||||
|
||||
|
||||
void *func() { return _addr; }
|
||||
|
||||
template<typename Result, typename... Args>
|
||||
Result invoke(Args... arguments)
|
||||
{
|
||||
Result res{};
|
||||
if(::VirtualProtect(_addr, size, PAGE_EXECUTE_READWRITE, &protect))
|
||||
{
|
||||
::memcpy(_addr, _orignal, sizeof(_orignal));
|
||||
using func_call = Result(__stdcall *)(Args... args);
|
||||
res = (func_call(_addr))(arguments...);
|
||||
::memcpy(_addr, _detour, sizeof(_detour));
|
||||
::VirtualProtect(_addr, size, protect, &protect);
|
||||
::FlushInstructionCache(::GetCurrentProcess(), _addr, size);
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
template<typename T = void *>
|
||||
T ink() const { return (T)_addr; }
|
||||
};
|
||||
*/
|
||||
|
||||
class WindowsHook
|
||||
{
|
||||
private:
|
||||
HHOOK _handle{};
|
||||
int _idHook{};
|
||||
HOOKPROC _hookproc{};
|
||||
HINSTANCE _hModule{};
|
||||
DWORD _dwThreadId{};
|
||||
|
||||
public:
|
||||
HWND hWindow{};
|
||||
|
||||
WindowsHook()
|
||||
{
|
||||
init();
|
||||
}
|
||||
|
||||
~WindowsHook()
|
||||
{
|
||||
unhook();
|
||||
}
|
||||
|
||||
explicit operator bool() const { return _handle; }
|
||||
explicit operator HHOOK() const { return _handle; }
|
||||
|
||||
HHOOK get() const { return _handle; }
|
||||
|
||||
BOOL unhook()
|
||||
{
|
||||
if(_handle && Unhook(_handle))
|
||||
_handle = nullptr;
|
||||
return _handle == nullptr;
|
||||
}
|
||||
|
||||
BOOL hook(int idHook, HOOKPROC hookproc, HWND hWnd)
|
||||
{
|
||||
return hook(idHook, hookproc, nullptr, ::GetWindowThreadProcessId(hWnd, nullptr));
|
||||
}
|
||||
|
||||
BOOL hook(int idHook, HOOKPROC hookproc, DWORD dwThreadId)
|
||||
{
|
||||
return hook(idHook, hookproc, nullptr, dwThreadId);
|
||||
}
|
||||
|
||||
BOOL hook(int idHook, HOOKPROC hookproc, HMODULE hModule, DWORD dwThreadId)
|
||||
{
|
||||
unhook();
|
||||
_idHook = idHook;
|
||||
_hookproc = hookproc;
|
||||
_hModule = hModule;
|
||||
_dwThreadId = dwThreadId;
|
||||
_handle = Hook(idHook, hookproc, hModule, dwThreadId);
|
||||
return _handle != nullptr;
|
||||
}
|
||||
|
||||
LRESULT callnext(int nCode, WPARAM wParam, LPARAM lParam) const
|
||||
{
|
||||
return CallNext(_handle, nCode, wParam, lParam);
|
||||
}
|
||||
|
||||
static HHOOK Hook(int idHook, HOOKPROC lpfn, HINSTANCE hmod, DWORD dwThreadId)
|
||||
{
|
||||
if(!init()) return 0;
|
||||
return _setWindowsHookExW(idHook, lpfn, hmod, dwThreadId);
|
||||
}
|
||||
|
||||
static BOOL Unhook(HHOOK handle)
|
||||
{
|
||||
if(!init()) return 0;
|
||||
return !handle ? 0 : _unhookWindowsHookEx(handle);
|
||||
}
|
||||
|
||||
static LRESULT CallNext(HHOOK handle, int nCode, WPARAM wParam, LPARAM lParam)
|
||||
{
|
||||
if(!init()) return 0;
|
||||
return _callNext(handle, nCode, wParam, lParam);
|
||||
}
|
||||
|
||||
static bool init()
|
||||
{
|
||||
if(!user32_hModule)
|
||||
user32_hModule = ::GetModuleHandleW(L"user32.dll");
|
||||
|
||||
if(user32_hModule)
|
||||
{
|
||||
if(!_setWindowsHookExW)
|
||||
_setWindowsHookExW = (LPFSetWindowsHookExW)::GetProcAddress(user32_hModule, "SetWindowsHookExW");
|
||||
|
||||
if(!_callNext)
|
||||
_callNext = (LPFCallNext)::GetProcAddress(user32_hModule, "CallNextHookEx");
|
||||
|
||||
if(!_unhookWindowsHookEx)
|
||||
_unhookWindowsHookEx = (LPFUnhookWindowsHookEx)::GetProcAddress(user32_hModule, "UnhookWindowsHookEx");
|
||||
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
private:
|
||||
using LPFUnhookWindowsHookEx = BOOL(__stdcall *)(HHOOK handle);
|
||||
using LPFSetWindowsHookExW = HHOOK(__stdcall *)(int idHook, HOOKPROC lpfn, HINSTANCE hmod, DWORD dwThreadId);
|
||||
using LPFCallNext = LRESULT(__stdcall *)(HHOOK handle, int nCode, WPARAM wParam, LPARAM lParam);
|
||||
|
||||
inline static HMODULE user32_hModule = nullptr;
|
||||
inline static LPFCallNext _callNext = nullptr;
|
||||
inline static LPFUnhookWindowsHookEx _unhookWindowsHookEx = nullptr;
|
||||
inline static LPFSetWindowsHookExW _setWindowsHookExW = nullptr;
|
||||
};
|
||||
|
||||
class WinEventHook
|
||||
{
|
||||
HWINEVENTHOOK _handle{};
|
||||
|
||||
public:
|
||||
WinEventHook() {}
|
||||
|
||||
~WinEventHook()
|
||||
{
|
||||
unhook();
|
||||
}
|
||||
|
||||
explicit operator bool() const { return _handle; }
|
||||
explicit operator HWINEVENTHOOK() const { return _handle; }
|
||||
|
||||
HWINEVENTHOOK get() const { return _handle; }
|
||||
|
||||
BOOL unhook()
|
||||
{
|
||||
if(_handle && ::UnhookWinEvent(_handle))
|
||||
_handle = nullptr;
|
||||
return _handle == nullptr;
|
||||
}
|
||||
|
||||
BOOL hook(DWORD eventMin, DWORD eventMax, HMODULE hmodWinEventProc, WINEVENTPROC pfnWinEventProc, DWORD idProcess, DWORD idThread, DWORD dwFlags = WINEVENT_INCONTEXT)
|
||||
{
|
||||
_handle = ::SetWinEventHook(eventMin, eventMax, hmodWinEventProc, pfnWinEventProc, idProcess, idThread, dwFlags);
|
||||
return _handle != nullptr;
|
||||
}
|
||||
};
|
||||
|
||||
class WindowSubclass
|
||||
{
|
||||
HWND _hWnd{};
|
||||
SUBCLASSPROC _subclass{};
|
||||
UINT_PTR _uIdSubclass{};
|
||||
DWORD_PTR _dwRefData{};
|
||||
bool _hooked {};
|
||||
|
||||
public:
|
||||
WindowSubclass() {}
|
||||
~WindowSubclass()
|
||||
{
|
||||
unhook();
|
||||
}
|
||||
|
||||
explicit operator bool() const { return _hooked; }
|
||||
|
||||
BOOL hook(HWND hWnd, SUBCLASSPROC pfnSubclass, UINT_PTR uIdSubclass, auto dwRefData)
|
||||
{
|
||||
_hWnd = hWnd;
|
||||
_subclass = pfnSubclass;
|
||||
_uIdSubclass = uIdSubclass;
|
||||
_dwRefData = reinterpret_cast<DWORD_PTR>(dwRefData);
|
||||
_hooked = Set(hWnd, pfnSubclass, uIdSubclass, _dwRefData);
|
||||
return _hooked;
|
||||
}
|
||||
|
||||
BOOL unhook()
|
||||
{
|
||||
if(_subclass)
|
||||
Remove(_hWnd, _subclass, _uIdSubclass);
|
||||
|
||||
_hWnd = {};
|
||||
_subclass = {};
|
||||
_uIdSubclass = {};
|
||||
_dwRefData = {};
|
||||
_hooked={};
|
||||
|
||||
return _hooked;
|
||||
}
|
||||
|
||||
//template<typename T>
|
||||
static BOOL Set(HWND hWnd, SUBCLASSPROC pfnSubclass, UINT_PTR uIdSubclass, auto dwRefData)
|
||||
{
|
||||
return ::SetWindowSubclass(hWnd, pfnSubclass, uIdSubclass, (DWORD_PTR)dwRefData);
|
||||
}
|
||||
|
||||
static BOOL Remove(HWND hWnd, SUBCLASSPROC pfnSubclass, UINT_PTR uIdSubclass)
|
||||
{
|
||||
return ::RemoveWindowSubclass(hWnd, pfnSubclass, uIdSubclass);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
static BOOL Get(HWND hWnd, SUBCLASSPROC pfnSubclass, UINT_PTR uIdSubclass, T *dwRefData)
|
||||
{
|
||||
return ::GetWindowSubclass(hWnd, pfnSubclass, uIdSubclass, static_cast<DWORD_PTR*>(dwRefData));
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
@@ -0,0 +1,687 @@
|
||||
#pragma once
|
||||
#include "Include/Theme.h"
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
struct D2D_DC
|
||||
{
|
||||
inline static ID2D1Factory *D2D1Factory = nullptr;
|
||||
inline static IDWriteFactory *DWriteFactory = nullptr;
|
||||
inline static ID2D1DCRenderTarget *render = nullptr;
|
||||
|
||||
inline static IDWriteTextFormat *textFormat = nullptr;
|
||||
inline static ID2D1SolidColorBrush *brush = nullptr;
|
||||
|
||||
~D2D_DC()
|
||||
{
|
||||
D2D1Factory = release(D2D1Factory);
|
||||
DWriteFactory = release(DWriteFactory);
|
||||
render = release(render);
|
||||
textFormat = release(textFormat);
|
||||
brush = release(brush);
|
||||
}
|
||||
|
||||
static void reset_target()
|
||||
{
|
||||
if(render)
|
||||
render->Release();
|
||||
render = nullptr;
|
||||
}
|
||||
|
||||
static bool init()
|
||||
{
|
||||
HRESULT hr = S_OK;
|
||||
|
||||
if(!D2D1Factory)
|
||||
{
|
||||
hr = ::D2D1CreateFactory(D2D1_FACTORY_TYPE_SINGLE_THREADED, {}, &D2D1Factory);
|
||||
if(hr != S_OK)
|
||||
return false;
|
||||
}
|
||||
|
||||
if(!DWriteFactory)
|
||||
{
|
||||
hr = ::DWriteCreateFactory(DWRITE_FACTORY_TYPE_SHARED, __uuidof(DWriteFactory), reinterpret_cast<IUnknown **>(&DWriteFactory));
|
||||
}
|
||||
|
||||
return hr == S_OK;
|
||||
}
|
||||
|
||||
static bool init_res()
|
||||
{
|
||||
if(init() && create_render())
|
||||
{
|
||||
return create_res();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
static bool create_render()
|
||||
{
|
||||
if(init() && !render)
|
||||
{
|
||||
D2D1Factory->CreateDCRenderTarget(&props, &render);
|
||||
}
|
||||
return render;
|
||||
}
|
||||
|
||||
static IDWriteTextFormat *createTextFormat(LPCWSTR name, int size, DWRITE_FONT_WEIGHT weight = DWRITE_FONT_WEIGHT_NORMAL,
|
||||
DWRITE_FONT_STYLE style = DWRITE_FONT_STYLE_NORMAL)
|
||||
{
|
||||
IDWriteTextFormat *_textFormat = nullptr;
|
||||
if(DWriteFactory)
|
||||
DWriteFactory->CreateTextFormat(name, nullptr, weight, style, DWRITE_FONT_STRETCH_NORMAL, (float)size, L"", &_textFormat);
|
||||
return _textFormat;
|
||||
}
|
||||
|
||||
static ID2D1SolidColorBrush *createSolidColorBrush(D2D1::ColorF color)
|
||||
{
|
||||
ID2D1SolidColorBrush *_brush = nullptr;
|
||||
if(render)
|
||||
render->CreateSolidColorBrush(color, &_brush);
|
||||
return _brush;
|
||||
}
|
||||
|
||||
static bool create_res()
|
||||
{
|
||||
if(!brush)
|
||||
{
|
||||
brush = createSolidColorBrush(D2D1::ColorF::White);
|
||||
}
|
||||
//if(!textFormat)
|
||||
// textFormat = createTextFormat(L"Segoe UI", 12);
|
||||
|
||||
return brush;//&& textFormat;
|
||||
}
|
||||
|
||||
static void delete_res()
|
||||
{
|
||||
brush = release(brush);
|
||||
textFormat = release(textFormat);
|
||||
}
|
||||
|
||||
static HRESULT bind(HDC hDC, const Rect rect)
|
||||
{
|
||||
create_render();
|
||||
return render ? render->BindDC(hDC, rect) : S_FALSE;
|
||||
}
|
||||
|
||||
static void begin()
|
||||
{
|
||||
if(create_render())
|
||||
render->BeginDraw();
|
||||
}
|
||||
|
||||
static HRESULT end(bool reset = false)
|
||||
{
|
||||
HRESULT hr = S_FALSE;
|
||||
if(render)
|
||||
{
|
||||
hr = render->EndDraw();
|
||||
if(reset && hr == D2DERR_RECREATE_TARGET)
|
||||
{
|
||||
reset_target();
|
||||
}
|
||||
}
|
||||
return hr;
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
static T *release(T *obj)
|
||||
{
|
||||
if(obj) obj->Release();
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
private:
|
||||
inline static const D2D1_RENDER_TARGET_PROPERTIES props = D2D1::RenderTargetProperties(
|
||||
D2D1_RENDER_TARGET_TYPE_DEFAULT,
|
||||
D2D1::PixelFormat(DXGI_FORMAT_B8G8R8A8_UNORM, D2D1_ALPHA_MODE_PREMULTIPLIED),
|
||||
0,
|
||||
0,
|
||||
D2D1_RENDER_TARGET_USAGE_NONE,
|
||||
D2D1_FEATURE_LEVEL_DEFAULT
|
||||
);
|
||||
};
|
||||
/*
|
||||
struct D2D_DC
|
||||
{
|
||||
inline static ID2D1Factory *D2D1Factory = nullptr;
|
||||
inline static IDWriteFactory *DWriteFactory = nullptr;
|
||||
|
||||
ID2D1DCRenderTarget *render = nullptr;
|
||||
IDWriteTextFormat *textFormat = nullptr;
|
||||
ID2D1SolidColorBrush *brush = nullptr;
|
||||
|
||||
HDC _hdc = nullptr;
|
||||
RECT _size;
|
||||
|
||||
D2D_DC()
|
||||
{
|
||||
}
|
||||
|
||||
D2D_DC(HDC hwnd, RECT rc)
|
||||
: _hdc{ hwnd }, _size({ w, h })
|
||||
{
|
||||
}
|
||||
|
||||
~D2D_DC()
|
||||
{
|
||||
D2D1Factory = release(D2D1Factory);
|
||||
DWriteFactory = release(DWriteFactory);
|
||||
render = release(render);
|
||||
textFormat = release(textFormat);
|
||||
brush = release(brush);
|
||||
}
|
||||
|
||||
bool create_render(HWND hwnd, uint32_t w, uint32_t h)
|
||||
{
|
||||
//_hwnd = hwnd;
|
||||
//_size = { w, h };
|
||||
return create_render();
|
||||
}
|
||||
|
||||
bool create_render()
|
||||
{
|
||||
if(init() && !render)
|
||||
{
|
||||
D2D1Factory->CreateDCRenderTarget(&props, &render);
|
||||
}
|
||||
return render;
|
||||
}
|
||||
|
||||
HRESULT bind(HDC hDC, RECT *pSubRect)
|
||||
{
|
||||
create_render();
|
||||
return render ? render->BindDC(hDC, pSubRect) : S_FALSE;
|
||||
}
|
||||
|
||||
void begin()
|
||||
{
|
||||
if(create_render())
|
||||
render->BeginDraw();
|
||||
}
|
||||
|
||||
HRESULT end(bool reset = false)
|
||||
{
|
||||
HRESULT hr = S_FALSE;
|
||||
if(render)
|
||||
{
|
||||
hr = render->EndDraw();
|
||||
if(reset && hr == D2DERR_RECREATE_TARGET)
|
||||
{
|
||||
reset_target();
|
||||
}
|
||||
}
|
||||
return hr;
|
||||
}
|
||||
|
||||
void reset_target()
|
||||
{
|
||||
if(render)
|
||||
render->Release();
|
||||
render = nullptr;
|
||||
}
|
||||
|
||||
static bool init()
|
||||
{
|
||||
HRESULT hr = S_OK;
|
||||
|
||||
if(!D2D1Factory)
|
||||
{
|
||||
hr = ::D2D1CreateFactory(D2D1_FACTORY_TYPE_SINGLE_THREADED, {}, &D2D1Factory);
|
||||
if(hr != S_OK)
|
||||
return false;
|
||||
}
|
||||
|
||||
if(!DWriteFactory)
|
||||
{
|
||||
hr = ::DWriteCreateFactory(DWRITE_FACTORY_TYPE_SHARED, __uuidof(DWriteFactory), reinterpret_cast<IUnknown **>(&DWriteFactory));
|
||||
}
|
||||
|
||||
return hr == S_OK;
|
||||
}
|
||||
|
||||
bool init_res()
|
||||
{
|
||||
if(init() && create_render())
|
||||
{
|
||||
return create_res();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
static IDWriteTextFormat *createTextFormat(LPCWSTR name, int size, DWRITE_FONT_WEIGHT weight = DWRITE_FONT_WEIGHT_NORMAL, DWRITE_FONT_STYLE style = DWRITE_FONT_STYLE_NORMAL)
|
||||
{
|
||||
IDWriteTextFormat *_textFormat = nullptr;
|
||||
if(DWriteFactory)
|
||||
DWriteFactory->CreateTextFormat(name, nullptr, weight, style, DWRITE_FONT_STRETCH_NORMAL, (float)size, L"", &_textFormat);
|
||||
return _textFormat;
|
||||
}
|
||||
|
||||
ID2D1SolidColorBrush *createSolidColorBrush(D2D1::ColorF color)
|
||||
{
|
||||
ID2D1SolidColorBrush *_brush = nullptr;
|
||||
if(render)
|
||||
render->CreateSolidColorBrush(color, &_brush);
|
||||
return _brush;
|
||||
}
|
||||
|
||||
bool create_res()
|
||||
{
|
||||
if(!brush)
|
||||
{
|
||||
brush = createSolidColorBrush(D2D1::ColorF::White);
|
||||
}
|
||||
//if(!textFormat)
|
||||
// textFormat = createTextFormat(L"Segoe UI", 12);
|
||||
|
||||
return brush;//&& textFormat;
|
||||
}
|
||||
|
||||
void delete_res()
|
||||
{
|
||||
brush = release(brush);
|
||||
textFormat = release(textFormat);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
static T *release(T *obj)
|
||||
{
|
||||
if(obj) obj->Release();
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
private:
|
||||
inline static const D2D1_RENDER_TARGET_PROPERTIES props = D2D1::RenderTargetProperties(
|
||||
D2D1_RENDER_TARGET_TYPE_DEFAULT,
|
||||
D2D1::PixelFormat(DXGI_FORMAT_B8G8R8A8_UNORM, D2D1_ALPHA_MODE_PREMULTIPLIED),
|
||||
0,
|
||||
0,
|
||||
D2D1_RENDER_TARGET_USAGE_NONE,
|
||||
D2D1_FEATURE_LEVEL_DEFAULT
|
||||
);
|
||||
};
|
||||
*/
|
||||
struct D2D
|
||||
{
|
||||
inline static ID2D1Factory *D2D1Factory = nullptr;
|
||||
inline static IDWriteFactory *DWriteFactory = nullptr;
|
||||
|
||||
ID2D1DCRenderTarget *render = nullptr;
|
||||
IDWriteTextFormat *textFormat = nullptr;
|
||||
ID2D1SolidColorBrush *brush = nullptr;
|
||||
ID2D1StrokeStyle *stroke = nullptr;
|
||||
|
||||
HDC _hdc = nullptr;
|
||||
RECT _rect{};
|
||||
|
||||
D2D()
|
||||
{
|
||||
}
|
||||
|
||||
D2D(HDC hdc, RECT rect)
|
||||
: _hdc{ hdc }, _rect{ rect }
|
||||
{
|
||||
}
|
||||
|
||||
~D2D()
|
||||
{
|
||||
render = release(render);
|
||||
textFormat = release(textFormat);
|
||||
brush = release(brush);
|
||||
}
|
||||
|
||||
static void destroy_Factory()
|
||||
{
|
||||
D2D1Factory = release(D2D1Factory);
|
||||
DWriteFactory = release(DWriteFactory);
|
||||
}
|
||||
|
||||
bool create_render(HDC hdc, RECT rect)
|
||||
{
|
||||
_hdc = hdc;
|
||||
_rect = rect;
|
||||
return create_render();
|
||||
}
|
||||
|
||||
bool create_render()
|
||||
{
|
||||
if(init() && !render)
|
||||
{
|
||||
D2D1Factory->CreateDCRenderTarget(&props, &render);
|
||||
}
|
||||
return render;
|
||||
}
|
||||
|
||||
HRESULT bind()
|
||||
{
|
||||
create_render();
|
||||
return render ? render->BindDC(_hdc, &_rect) : S_FALSE;
|
||||
}
|
||||
|
||||
HRESULT bind(HDC hdc, const Rect rect)
|
||||
{
|
||||
_hdc = hdc;
|
||||
_rect = rect;
|
||||
return bind();
|
||||
}
|
||||
|
||||
void begin()
|
||||
{
|
||||
if(create_render())
|
||||
render->BeginDraw();
|
||||
}
|
||||
|
||||
void begin(HDC hdc, const Rect rect)
|
||||
{
|
||||
if(init_res())
|
||||
{
|
||||
bind(hdc, rect);
|
||||
//if(SUCCEEDED())
|
||||
{
|
||||
|
||||
render->BeginDraw();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
HRESULT end(bool reset = false)
|
||||
{
|
||||
HRESULT hr = S_FALSE;
|
||||
if(render)
|
||||
{
|
||||
hr = render->EndDraw();
|
||||
if(reset && hr == D2DERR_RECREATE_TARGET)
|
||||
{
|
||||
reset_target();
|
||||
}
|
||||
}
|
||||
return hr;
|
||||
}
|
||||
|
||||
void reset_target()
|
||||
{
|
||||
if(render)
|
||||
render->Release();
|
||||
render = nullptr;
|
||||
}
|
||||
|
||||
static bool init()
|
||||
{
|
||||
HRESULT hr = S_OK;
|
||||
|
||||
if(!D2D1Factory)
|
||||
{
|
||||
hr = ::D2D1CreateFactory(D2D1_FACTORY_TYPE_SINGLE_THREADED, {}, &D2D1Factory);
|
||||
if(hr != S_OK)
|
||||
return false;
|
||||
}
|
||||
|
||||
if(!DWriteFactory)
|
||||
{
|
||||
hr = ::DWriteCreateFactory(DWRITE_FACTORY_TYPE_SHARED,
|
||||
__uuidof(DWriteFactory),
|
||||
reinterpret_cast<IUnknown **>(&DWriteFactory));
|
||||
}
|
||||
|
||||
return hr == S_OK;
|
||||
}
|
||||
|
||||
bool init_res()
|
||||
{
|
||||
if(init() && create_render())
|
||||
{
|
||||
return create_res();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
static IDWriteTextFormat *createTextFormat(LPCWSTR name, int size,
|
||||
DWRITE_FONT_WEIGHT weight = DWRITE_FONT_WEIGHT_NORMAL,
|
||||
DWRITE_FONT_STYLE style = DWRITE_FONT_STYLE_NORMAL)
|
||||
{
|
||||
|
||||
IDWriteTextFormat *_textFormat = nullptr;
|
||||
if(DWriteFactory)
|
||||
DWriteFactory->CreateTextFormat(name, nullptr, weight, style, DWRITE_FONT_STRETCH_NORMAL, (float)size, L"", &_textFormat);
|
||||
return _textFormat;
|
||||
}
|
||||
|
||||
static ID2D1StrokeStyle *createStrokeStyle()
|
||||
{
|
||||
// Dash array for dashStyle D2D1_DASH_STYLE_CUSTOM
|
||||
//float dashes[] = { 1.0f, 2.0f, 2.0f, 3.0f, 2.0f, 2.0f };
|
||||
ID2D1StrokeStyle *stroke = nullptr;
|
||||
if(DWriteFactory)
|
||||
{
|
||||
D2D1Factory->CreateStrokeStyle(
|
||||
D2D1::StrokeStyleProperties(
|
||||
D2D1_CAP_STYLE_ROUND,
|
||||
D2D1_CAP_STYLE_ROUND,
|
||||
D2D1_CAP_STYLE_ROUND,
|
||||
D2D1_LINE_JOIN_ROUND,
|
||||
0.0f,
|
||||
D2D1_DASH_STYLE_SOLID,
|
||||
0.0f),
|
||||
nullptr,
|
||||
0,
|
||||
&stroke
|
||||
);
|
||||
}
|
||||
return stroke;
|
||||
}
|
||||
|
||||
ID2D1SolidColorBrush *createSolidColorBrush(D2D1::ColorF color)
|
||||
{
|
||||
if(render)
|
||||
render->CreateSolidColorBrush(color, &brush);
|
||||
return brush;
|
||||
}
|
||||
|
||||
bool create_res()
|
||||
{
|
||||
if(render)
|
||||
{
|
||||
if(!brush)
|
||||
brush = createSolidColorBrush(D2D1::ColorF::White);
|
||||
//if(!textFormat)
|
||||
// textFormat = createTextFormat(L"Segoe UI", 12);
|
||||
}
|
||||
|
||||
if(!stroke)
|
||||
stroke = createStrokeStyle();
|
||||
return brush;//&& textFormat;
|
||||
}
|
||||
|
||||
void delete_res()
|
||||
{
|
||||
brush = release(brush);
|
||||
textFormat = release(textFormat);
|
||||
}
|
||||
|
||||
template<typename T>
|
||||
static T *release(T *obj)
|
||||
{
|
||||
if(obj) obj->Release();
|
||||
return nullptr;
|
||||
}
|
||||
/*
|
||||
ID2D1PathGeometry *CreateRoundRect(int x, int y, int width, int height, int leftTop, int rightTop, int rightBottom, int leftBottom)
|
||||
{
|
||||
ID2D1GeometrySink *sink = nullptr;
|
||||
ID2D1PathGeometry *path = nullptr;
|
||||
|
||||
D2D1Factory->CreatePathGeometry(&path);
|
||||
path->Open(&sink);
|
||||
|
||||
D2D1_POINT_2F p[2];
|
||||
|
||||
p[0].x = x + leftTop;
|
||||
p[0].y = y;
|
||||
sink->BeginFigure(p[0], D2D1_FIGURE_BEGIN::D2D1_FIGURE_BEGIN_FILLED);
|
||||
p[1].x = x + width - rightTop;
|
||||
p[1].y = y;
|
||||
sink->AddLines(p, 2);
|
||||
|
||||
p[0].x = x + width;
|
||||
p[0].y = y + rightTop;
|
||||
|
||||
if(rightTop)
|
||||
{
|
||||
D2D1_POINT_2F p2 = D2D1::Matrix3x2F::Rotation(0, p[1]).TransformPoint(p[0]);
|
||||
sink->AddArc(D2D1::ArcSegment(p2, D2D1::SizeF(rightTop, rightTop), 0, D2D1_SWEEP_DIRECTION_CLOCKWISE, D2D1_ARC_SIZE_SMALL));
|
||||
}
|
||||
|
||||
p[1].x = x + width;
|
||||
p[1].y = y + height - rightBottom;
|
||||
sink->AddLines(p, 2);
|
||||
|
||||
p[0].x = x + width - rightBottom;
|
||||
p[0].y = y + height;
|
||||
|
||||
if(rightBottom)
|
||||
{
|
||||
D2D1_POINT_2F p2 = D2D1::Matrix3x2F::Rotation(0, p[1]).TransformPoint(p[0]);
|
||||
sink->AddArc(D2D1::ArcSegment(p2, D2D1::SizeF(rightBottom, rightBottom), 0, D2D1_SWEEP_DIRECTION_CLOCKWISE, D2D1_ARC_SIZE_SMALL));
|
||||
}
|
||||
|
||||
p[1].x = x + leftBottom;
|
||||
p[1].y = y + height;
|
||||
sink->AddLines(p, 2);
|
||||
|
||||
p[0].x = x;
|
||||
p[0].y = y + height - leftBottom;
|
||||
if(leftBottom)
|
||||
{
|
||||
D2D1_POINT_2F p2 = D2D1::Matrix3x2F::Rotation(0, p[1]).TransformPoint(p[0]);
|
||||
sink->AddArc(D2D1::ArcSegment(p2, D2D1::SizeF(leftBottom, leftBottom), 0, D2D1_SWEEP_DIRECTION_CLOCKWISE, D2D1_ARC_SIZE_SMALL));
|
||||
}
|
||||
|
||||
|
||||
p[1].x = x;
|
||||
p[1].y = y + leftTop;
|
||||
sink->AddLines(p, 2);
|
||||
p[0].x = x + leftTop;
|
||||
p[0].y = y;
|
||||
if(leftTop)
|
||||
{
|
||||
D2D1_POINT_2F p2 = D2D1::Matrix3x2F::Rotation(0, p[1]).TransformPoint(p[0]);
|
||||
sink->AddArc(D2D1::ArcSegment(p2, D2D1::SizeF(leftTop, leftTop), 0, D2D1_SWEEP_DIRECTION_CLOCKWISE, D2D1_ARC_SIZE_SMALL));
|
||||
}
|
||||
|
||||
sink->EndFigure(D2D1_FIGURE_END::D2D1_FIGURE_END_CLOSED);
|
||||
sink->Close();
|
||||
release(&sink);
|
||||
|
||||
return path;
|
||||
}*/
|
||||
|
||||
private:
|
||||
inline static const D2D1_RENDER_TARGET_PROPERTIES props = D2D1::RenderTargetProperties(
|
||||
D2D1_RENDER_TARGET_TYPE_DEFAULT,
|
||||
D2D1::PixelFormat(DXGI_FORMAT_B8G8R8A8_UNORM, D2D1_ALPHA_MODE_PREMULTIPLIED),
|
||||
0,
|
||||
0,
|
||||
D2D1_RENDER_TARGET_USAGE_NONE,
|
||||
D2D1_FEATURE_LEVEL_DEFAULT
|
||||
);
|
||||
};
|
||||
|
||||
class Initializer
|
||||
{
|
||||
private:
|
||||
uintptr_t _last_write_time{};
|
||||
|
||||
public:
|
||||
struct {
|
||||
HMODULE hModule{};
|
||||
HANDLE handle{};
|
||||
DWORD id{};
|
||||
string name;
|
||||
string path;
|
||||
} process;
|
||||
|
||||
Application application;
|
||||
HRESULT com_init = E_UNEXPECTED;
|
||||
COM_INITIALIZER com_initializer;
|
||||
bool is_elevated{};
|
||||
CACHE *cache{};
|
||||
//Hooker user32_TrackPopupMenu;
|
||||
//Hooker user32_TrackPopupMenuEx;
|
||||
//Hooker user32u_TrackPopupMenuEx;
|
||||
uint32_t dpi = 96;
|
||||
|
||||
Initializer() { instance = this; };
|
||||
~Initializer();
|
||||
|
||||
bool query(int ch = 0);
|
||||
bool init(HINSTANCE hInstance);
|
||||
bool init();
|
||||
// Clean up resources allocated during initialization.
|
||||
bool uninit();
|
||||
|
||||
//reloadOnChange
|
||||
//determine
|
||||
bool config_has_changed();
|
||||
bool has_error(bool detect_changes = false);
|
||||
void load_mui();
|
||||
|
||||
struct STATUS { bool Loaded, Disabled, Refresh, Error; } inline static Status{};
|
||||
|
||||
struct LASTERROR
|
||||
{
|
||||
TokenError code{};
|
||||
uint32_t line, col{};
|
||||
} inline static LastError{};
|
||||
|
||||
public:
|
||||
inline static Initializer *instance{};
|
||||
inline static HINSTANCE HInstance{};
|
||||
|
||||
static bool Inited()
|
||||
{
|
||||
return Status.Loaded;
|
||||
}
|
||||
|
||||
//static HRESULT Modern(int enabled);
|
||||
static bool OnState(bool istaskbar = false);
|
||||
|
||||
inline static std::unordered_map<uint32_t, MUID> MAP_MUID;
|
||||
|
||||
static MUID* get_muid(uint32_t hash)
|
||||
{
|
||||
for(auto &it : MAP_MUID)
|
||||
{
|
||||
if(it.first == hash or it.second.hash == hash)
|
||||
return &it.second;
|
||||
}
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
static uint32_t get_hash(uint32_t id)
|
||||
{
|
||||
for(auto &it : MAP_MUID)
|
||||
{
|
||||
if(it.first == id)
|
||||
return it.second.hash;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
static bool IsLanguageRTL(void)
|
||||
{
|
||||
LOCALESIGNATURE localesig{};
|
||||
LANGID language = ::GetUserDefaultUILanguage();
|
||||
if(::GetLocaleInfoW(language, LOCALE_FONTSIGNATURE,
|
||||
(LPWSTR)&localesig,
|
||||
(sizeof(localesig) / sizeof(wchar_t))) && (localesig.lsUsb[3] & 0x08000000))
|
||||
return true;
|
||||
return false;
|
||||
}*/
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,184 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
class Keyboard
|
||||
{
|
||||
uint8_t _KEYS[128] =
|
||||
{
|
||||
{0x01},{0x02},{0x03},{0x04},{0x05},{0x06},{0x08},{0x09},{0x0C},{0x0D},{0x13},{0x14},{0x15},{0x16},{0x17},{0x18},
|
||||
{0x19},{0x1A},{0x1B},{0x1C},{0x1D},{0x1E},{0x1F},{0x20},{0x21},{0x22},{0x23},{0x24},{0x25},{0x26},{0x27},{0x28},
|
||||
{0x29},{0x2A},{0x2B},{0x2C},{0x2D},{0x2E},{0x2F},{0x30},{0x31},{0x32},{0x33},{0x34},{0x35},{0x36},{0x37},{0x38},
|
||||
{0x39},{0x41},{0x42},{0x43},{0x44},{0x45},{0x46},{0x47},{0x48},{0x49},{0x4A},{0x4B},{0x4C},{0x4D},{0x4E},{0x4F},
|
||||
{0x50},{0x51},{0x52},{0x53},{0x54},{0x55},{0x56},{0x57},{0x58},{0x59},{0x5A},{0x5B},{0x5C},{0x5D},{0x5F},{0x60},
|
||||
{0x61},{0x62},{0x63},{0x64},{0x65},{0x66},{0x67},{0x68},{0x69},{0x6A},{0x6B},{0x6C},{0x6D},{0x6E},{0x6F},{0x70},
|
||||
{0x71},{0x72},{0x73},{0x74},{0x75},{0x76},{0x77},{0x78},{0x79},{0x7A},{0x7B},{0x7C},{0x7D},{0x7E},{0x7F},{0x80},
|
||||
{0x81},{0x82},{0x83},{0x84},{0x85},{0x86},{0x87},{0x90},{0x91},{0x92},{0xA0},{0xA1},{0xA2},{0xA3},{0xA4},{0xA5}
|
||||
};
|
||||
|
||||
std::vector<uint8_t> _keys;
|
||||
uint8_t _has_contextmenu = 0;
|
||||
|
||||
public:
|
||||
Keyboard(bool init = false)
|
||||
{
|
||||
reset();
|
||||
if(init) get_keys_state();
|
||||
}
|
||||
|
||||
void reset()
|
||||
{
|
||||
_keys.clear();
|
||||
}
|
||||
|
||||
uint8_t get_keys_state(bool async = true)
|
||||
{
|
||||
reset();
|
||||
|
||||
auto swb = IsSwapButton();
|
||||
|
||||
for(auto key : _KEYS)
|
||||
{
|
||||
if(IsKeyDown(key, async))
|
||||
{
|
||||
if(key == VK_LBUTTON && swb)
|
||||
_has_contextmenu = VK_LBUTTON;
|
||||
else if(key == VK_RBUTTON && !swb)
|
||||
_has_contextmenu = VK_RBUTTON;
|
||||
_keys.push_back(key);
|
||||
}
|
||||
}
|
||||
|
||||
if(!_has_contextmenu && key_shift() && key(VK_F10))
|
||||
_has_contextmenu = VK_SHIFT + VK_F10;
|
||||
return count();
|
||||
}
|
||||
|
||||
uint8_t get_keys_excloude_contextmenu()
|
||||
{
|
||||
reset();
|
||||
auto swb = IsSwapButton();
|
||||
for(auto key : _KEYS)
|
||||
{
|
||||
if(IsKeyDown(key, true))
|
||||
{
|
||||
if(key == VK_LBUTTON && swb)
|
||||
{
|
||||
_has_contextmenu = VK_LBUTTON;
|
||||
continue;
|
||||
}
|
||||
else if(key == VK_RBUTTON && !swb)
|
||||
{
|
||||
_has_contextmenu = VK_RBUTTON;
|
||||
continue;
|
||||
}
|
||||
_keys.push_back(key);
|
||||
}
|
||||
}
|
||||
|
||||
if(!_has_contextmenu)
|
||||
{
|
||||
if(key_shift() && key(VK_F10))
|
||||
{
|
||||
_has_contextmenu = VK_SHIFT + VK_F10;
|
||||
for(auto it = _keys.begin(); it != _keys.end(); it++)
|
||||
{
|
||||
if(*it == VK_LSHIFT || *it == VK_RSHIFT || *it == VK_F10)
|
||||
_keys.erase(it--);
|
||||
}
|
||||
}
|
||||
}
|
||||
return count();
|
||||
}
|
||||
|
||||
uint8_t count() const { return static_cast<uint8_t>(_keys.size()); }
|
||||
uint8_t first() const { return count() == 0 ? 0 : _keys.front(); }
|
||||
uint8_t last() const { return count() == 0 ? 0 : _keys.back();}
|
||||
|
||||
Keyboard& add_key(uint8_t key)
|
||||
{
|
||||
for(const auto k : _keys) {
|
||||
if(k == key)
|
||||
return *this;
|
||||
}
|
||||
_keys.push_back(key);
|
||||
return *this;
|
||||
}
|
||||
|
||||
bool key(uint8_t key) const
|
||||
{
|
||||
if(count() > 0)
|
||||
{
|
||||
for(auto k : _keys) if(k == key) return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool key(std::initializer_list<uint8_t> keys) const
|
||||
{
|
||||
for(auto k : keys) if(key(k)) return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
bool equals(std::initializer_list<uint8_t> keys) const
|
||||
{
|
||||
if(keys.size() == count())
|
||||
{
|
||||
for(auto k : keys)
|
||||
{
|
||||
if(!key(k)) return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool key_shift() const { return key({ VK_LSHIFT, VK_RSHIFT }); }
|
||||
bool key_lshift() const { return key(VK_LSHIFT); }
|
||||
bool key_srhift() const { return key(VK_RSHIFT); }
|
||||
|
||||
bool key_ctrl() const { return key({ VK_LCONTROL, VK_RCONTROL }); }
|
||||
bool key_lctrl() const { return key(VK_LCONTROL); }
|
||||
bool key_rctrl() const { return key(VK_RCONTROL); }
|
||||
|
||||
bool key_alt() const { return key({ VK_LMENU, VK_RMENU }); }
|
||||
bool key_lalt() const { return key(VK_LMENU); }
|
||||
bool key_ralt() const { return key(VK_RMENU); }
|
||||
|
||||
bool key_win() const { return key({ VK_LWIN, VK_RWIN }); }
|
||||
bool key_lwin() const { return key(VK_LWIN); }
|
||||
bool key_rwin() const { return key(VK_RWIN); }
|
||||
|
||||
bool has_contextmenu_func() const { return _has_contextmenu; }
|
||||
|
||||
bool is_contextmenu() const { return key_shift() && key(VK_F10); }
|
||||
bool is_rbutton() const { return key(VK_RBUTTON); }
|
||||
bool is_lbutton() const { return key(VK_LBUTTON); }
|
||||
bool is_mbutton() const { return key(VK_MBUTTON); }
|
||||
|
||||
uint8_t *begin() { return _keys.data(); }
|
||||
const uint8_t *begin() const { return begin(); }
|
||||
|
||||
uint8_t *end() { return _keys.data() + _keys.size(); }
|
||||
const uint8_t *end() const { return end(); }
|
||||
|
||||
static bool IsKeyDown(const std::initializer_list<uint8_t> &keys, bool async = true)
|
||||
{
|
||||
for(auto k : keys) if(IsKeyDown(k, async)) return true;
|
||||
return false;
|
||||
}
|
||||
|
||||
//is_pressed
|
||||
static bool IsKeyDown(uint8_t key, bool async = true) {
|
||||
return (0x8000 & (async ? ::GetAsyncKeyState(key) : ::GetKeyState(key))) == 0x8000;
|
||||
}
|
||||
|
||||
static bool IsSwapButton()
|
||||
{
|
||||
return ::GetSystemMetrics(SM_SWAPBUTTON);
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,378 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
constexpr auto NILESOFTSHELL_SIGN = 0x1989D5CDU;
|
||||
|
||||
struct IProperty
|
||||
{
|
||||
Expression *expr = nullptr;
|
||||
~IProperty() { delete expr; }
|
||||
};
|
||||
|
||||
struct Settings
|
||||
{
|
||||
auto_expr showdelay;
|
||||
auto_expr priority;
|
||||
struct
|
||||
{
|
||||
auto_expr enabled;
|
||||
auto_expr directory;
|
||||
}screenshot;
|
||||
|
||||
struct
|
||||
{
|
||||
auto_expr value;
|
||||
auto_expr window;
|
||||
auto_expr process;
|
||||
} exclude;
|
||||
|
||||
struct
|
||||
{
|
||||
auto_expr enabled;
|
||||
auto_expr auto_image_group;
|
||||
auto_expr auto_group;
|
||||
auto_expr auto_image;
|
||||
|
||||
auto_expr image;
|
||||
auto_expr title;
|
||||
auto_expr visibility;
|
||||
auto_expr parent;
|
||||
auto_expr position;
|
||||
auto_expr separator;
|
||||
auto_expr keys;
|
||||
struct
|
||||
{
|
||||
auto_expr disabled;
|
||||
auto_expr separator;
|
||||
auto_expr duplicate;
|
||||
}remove;
|
||||
} modify_items;
|
||||
|
||||
struct
|
||||
{
|
||||
auto_expr enabled;
|
||||
auto_expr image;
|
||||
auto_expr keys;
|
||||
} new_items;
|
||||
|
||||
struct MARGIN
|
||||
{
|
||||
uint32_t id = IDENT_MARGIN;
|
||||
auto_expr value;
|
||||
auto_expr left;
|
||||
auto_expr top;
|
||||
auto_expr right;
|
||||
auto_expr bottom;
|
||||
};
|
||||
|
||||
struct COLOR
|
||||
{
|
||||
auto_expr value;
|
||||
auto_expr normal;
|
||||
auto_expr select;
|
||||
auto_expr normal_disabled;
|
||||
auto_expr select_disabled;
|
||||
};
|
||||
|
||||
struct
|
||||
{
|
||||
auto_expr dark;
|
||||
auto_expr name;
|
||||
auto_expr view;
|
||||
|
||||
/*struct {
|
||||
auto_expr enabled;
|
||||
auto_expr color;
|
||||
auto_expr font;
|
||||
auto_expr size;
|
||||
} glyphs;*/
|
||||
|
||||
struct {
|
||||
auto_expr color;
|
||||
auto_expr opacity;
|
||||
auto_expr effect;
|
||||
auto_expr tintcolor;
|
||||
auto_expr image;
|
||||
} background;
|
||||
|
||||
struct
|
||||
{
|
||||
auto_expr enabled;
|
||||
auto_expr size;
|
||||
auto_expr color;
|
||||
auto_expr opacity;
|
||||
auto_expr radius;
|
||||
MARGIN padding;
|
||||
} border;
|
||||
|
||||
struct
|
||||
{
|
||||
auto_expr enabled;
|
||||
auto_expr size;
|
||||
auto_expr color;
|
||||
auto_expr opacity;
|
||||
auto_expr offset;
|
||||
} shadow;
|
||||
|
||||
struct
|
||||
{
|
||||
struct {
|
||||
COLOR color;
|
||||
auto_expr align;
|
||||
} text;
|
||||
|
||||
COLOR back;
|
||||
COLOR border;
|
||||
auto_expr opacity;
|
||||
auto_expr radius;
|
||||
MARGIN padding;
|
||||
MARGIN margin;
|
||||
auto_expr prefix;
|
||||
} item;
|
||||
|
||||
struct
|
||||
{
|
||||
auto_expr color;
|
||||
auto_expr size;
|
||||
auto_expr opacity;
|
||||
MARGIN margin;
|
||||
} separator;
|
||||
|
||||
struct {
|
||||
auto_expr value;
|
||||
auto_expr name;
|
||||
auto_expr size;
|
||||
auto_expr weight;
|
||||
auto_expr italic;
|
||||
} font;
|
||||
|
||||
struct
|
||||
{
|
||||
COLOR color;
|
||||
COLOR checkmark;
|
||||
COLOR bullet;
|
||||
COLOR chevron;
|
||||
auto_expr opacity;
|
||||
} symbol;
|
||||
|
||||
struct {
|
||||
auto_expr width;
|
||||
auto_expr rtl;
|
||||
struct {
|
||||
auto_expr align;
|
||||
}popup;
|
||||
}layout;
|
||||
|
||||
struct {
|
||||
auto_expr enabled;
|
||||
auto_expr linear;
|
||||
auto_expr radial;
|
||||
auto_expr stop;
|
||||
} gradient;
|
||||
|
||||
struct
|
||||
{
|
||||
auto_expr enabled;
|
||||
auto_expr color;
|
||||
auto_expr size;
|
||||
auto_expr opacity;
|
||||
auto_expr gap;
|
||||
auto_expr glyph;
|
||||
auto_expr scale;
|
||||
auto_expr display;
|
||||
} image;
|
||||
|
||||
} theme;
|
||||
|
||||
struct
|
||||
{
|
||||
auto_expr enabled;
|
||||
auto_expr normal;
|
||||
auto_expr primary;
|
||||
auto_expr success;
|
||||
auto_expr info;
|
||||
auto_expr warning;
|
||||
auto_expr danger;
|
||||
auto_expr border;
|
||||
auto_expr width;
|
||||
auto_expr opacity;
|
||||
auto_expr radius;
|
||||
auto_expr time;
|
||||
MARGIN padding;
|
||||
} tip;
|
||||
};
|
||||
|
||||
struct CommandProperty
|
||||
{
|
||||
struct : IProperty {
|
||||
int type = COMMAND_INVALID;
|
||||
} command;
|
||||
|
||||
/*struct : IProperty {
|
||||
Privileges value = Privileges::None;
|
||||
bool inherit = false;
|
||||
} admin;*/
|
||||
|
||||
auto_expr window;
|
||||
auto_expr directory;
|
||||
auto_expr verb;
|
||||
auto_expr wait;
|
||||
auto_expr admin;
|
||||
auto_expr invoke;
|
||||
auto_expr arguments;
|
||||
|
||||
bool inherit = false;
|
||||
|
||||
~CommandProperty()
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
enum class NativeMenuType : int32_t
|
||||
{
|
||||
None,
|
||||
Main,
|
||||
Menu, // SubMenu
|
||||
Item, // Command
|
||||
Separator // Spacer
|
||||
};
|
||||
|
||||
class NativeMenu
|
||||
{
|
||||
public:
|
||||
uint32_t sign = NILESOFTSHELL_SIGN + 1;
|
||||
|
||||
static constexpr auto TYPE_NONE = 0;
|
||||
static constexpr auto TYPE_MAIN = 1;
|
||||
static constexpr auto TYPE_MENU = 2;
|
||||
static constexpr auto TYPE_ITEM = 3;
|
||||
static constexpr auto TYPE_SEPARATOR = 4;
|
||||
|
||||
public:
|
||||
int32_t MenuId = 0;
|
||||
int32_t id = 0;
|
||||
NativeMenuType type = NativeMenuType::None;
|
||||
NativeMenu *owner{};
|
||||
Scope variables;
|
||||
int32_t for_each = 0;
|
||||
auto_expr expanded;
|
||||
std::vector<NativeMenu *> items;
|
||||
CommandProperty *cmd{};
|
||||
|
||||
uint32_t properties{};
|
||||
FileSystemObjects fso;
|
||||
auto_expr mode;
|
||||
auto_expr visibility;
|
||||
auto_expr tip;
|
||||
auto_expr position;
|
||||
auto_expr separator;
|
||||
auto_expr find;
|
||||
auto_expr location;
|
||||
auto_expr where;
|
||||
auto_expr keys;
|
||||
auto_expr moveto;
|
||||
auto_expr title;
|
||||
auto_expr checked;
|
||||
auto_expr column;
|
||||
// static item property
|
||||
auto_expr invoke;
|
||||
bool has_clsid = false;
|
||||
std::vector<Guid> clsid;
|
||||
|
||||
struct {
|
||||
auto_expr normal;
|
||||
auto_expr select;
|
||||
} images;
|
||||
|
||||
struct : IProperty {
|
||||
ImageImport import = ImageImport::None;
|
||||
bool inherit = false;
|
||||
bool defined = true;
|
||||
|
||||
bool enabled() const
|
||||
{
|
||||
return !(import == ImageImport::None || import == ImageImport::Disabled);
|
||||
}
|
||||
|
||||
bool disabled() const
|
||||
{
|
||||
return import == ImageImport::Disabled;
|
||||
}
|
||||
|
||||
} image;
|
||||
|
||||
std::vector<CommandProperty*> commands;
|
||||
|
||||
NativeMenu(NativeMenu *owner = nullptr) noexcept
|
||||
: owner(owner)
|
||||
{
|
||||
if(owner)
|
||||
{
|
||||
fso = owner->fso;
|
||||
variables.Parent = &owner->variables;
|
||||
}
|
||||
cmd = new CommandProperty;
|
||||
commands.push_back(cmd);
|
||||
}
|
||||
|
||||
NativeMenu(bool set_any_type) noexcept
|
||||
{
|
||||
fso.set(set_any_type);
|
||||
}
|
||||
|
||||
virtual ~NativeMenu()
|
||||
{
|
||||
/*if(owner)
|
||||
{
|
||||
if(mode.inherit)
|
||||
::memset(&mode, 0, sizeof(mode));
|
||||
|
||||
if(cmd->admin.inherit)
|
||||
cmd->admin.expr = nullptr;
|
||||
}
|
||||
*/
|
||||
for(auto it : items) delete it;
|
||||
for(auto it : commands) delete it;
|
||||
}
|
||||
|
||||
bool is_main() const { return (this->type == NativeMenuType::Main); }
|
||||
bool is_item() const { return (this->type == NativeMenuType::Item); }
|
||||
bool is_separator() const { return (this->type == NativeMenuType::Separator); }
|
||||
bool is_menu() const { return (this->type == NativeMenuType::Menu || this->type == NativeMenuType::Main); }
|
||||
|
||||
bool skip_separator(const std::vector<NativeMenu *> &list)
|
||||
{
|
||||
if(this->is_separator())
|
||||
{
|
||||
return(this == list.front() || this == list.back());
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
Expression *get_variable(uint32_t ident)
|
||||
{
|
||||
auto p = this->owner;
|
||||
while(p)
|
||||
{
|
||||
auto e = p->variables.at(ident);
|
||||
if(e) return e;
|
||||
p = p->owner;
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
static bool is_skip_separator(std::vector<NativeMenu*> const &list)
|
||||
{
|
||||
// front
|
||||
if(list.empty()) return true;
|
||||
// back
|
||||
return list.back()->is_separator();
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,350 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
constexpr auto NS_COMPUTER = 0xD4FD60C2U; //::{20D04FE0-3AEA-1069-A2D8-08002B30309D}
|
||||
constexpr auto NS_RECYCLE = 0xC8989B8EU; //::{645FF040-5081-101B-9F08-00AA002F954E}
|
||||
constexpr auto NS_CONTROL = 0x0AC95438U; //::{21EC2020-3AEA-1069-A2DD-08002B30309D}
|
||||
constexpr auto NS_NETWORK = 0xFF5E5EDEU; //::{F02C1A0D-BE21-4350-88B0-7367FC96EF3C}
|
||||
constexpr auto NS_NETWORKCENTER = 0x3E01EAF8U; //::{8E908FC9-BECC-40F6-915B-F4CA0E70D03D}
|
||||
constexpr auto NS_UINSTALL = 0x207A7697U; //::{7B81BE6A-CE2B-4676-A29E-EB907A5126C5}
|
||||
constexpr auto NS_SYSTEM = 0xE738C518U; //::{BB06C0E4-D293-4F75-8A90-CB05B6477EEE}
|
||||
constexpr auto NS_QUICKACCESS = 0xDB6BDBF5U; //::{679F85CB-0220-4080-B29B-5540CC05AAB6}
|
||||
constexpr auto NS_LIBRARIES = 0x214BFAA6U; //::{031E4825-7B94-4DC3-B131-E946B44C8DD5}
|
||||
//::{031E4825-7B94-4DC3-B131-E946B44C8DD5}\CameraRoll.library-ms
|
||||
/*
|
||||
|
||||
wnd cls=‘ShellTabWindowClass’ title=‘title*’
|
||||
wnd aaname=‘Explorer Pane’ cls=‘DirectUIHWND’
|
||||
wnd aaname=‘Shell Folder View’ cls=‘SHELLDLL_DefView’ title=‘ShellView’
|
||||
wnd aaname=‘Items View’ cls=‘DirectUIHWND’
|
||||
|
||||
*/
|
||||
//Windows Explorer on XP, Vista, 7, 8
|
||||
//hExplorer = WinGetHandle("[REGEXPCLASS:^(Cabinet|Explore)WClass$]")
|
||||
//CabinetWClass
|
||||
//ExploreWClass
|
||||
enum WindowClass : uint32_t
|
||||
{
|
||||
WC_NONE = 0,
|
||||
WC_APPLICATION = 0x00000001,
|
||||
WC_WorkerW = 0xD749CBB6, //L"WorkerW"
|
||||
WC_Progman = 0xC3394119, //L"Progman"
|
||||
//taskbar////
|
||||
WC_Shell_TrayWnd = 0x0CF03CA5, //taskbar
|
||||
WC_Shell_SecondaryTrayWnd = 0x3861CCEDU, // Shell_SecondaryTrayWnd
|
||||
WC_MSTASKLISTWCLASS = 0x8BFA5681U, // taskbar
|
||||
WC_TrayNotifyWnd = 0xFD59B287U,
|
||||
|
||||
WC__EDIT = 0x7C96292BU,
|
||||
WC__SEARCHEDITBOXFAKEWINDOW = 0xAF224CF8U, // _SearchEditBoxFakeWindow
|
||||
WC_BREADCRUMB = 0xDE0145C6U, // Breadcrumb Parent
|
||||
|
||||
WC__STATIC = 0x1C8A8BADU,//STATIC
|
||||
WC__BUTTON = 0xF4FF5D81U,
|
||||
WC_START = 0x106149D3U,
|
||||
WC_LauncherTipWnd = 0x41DE6ECDU, //// Win+X menu
|
||||
WC_TrayShowDesktopButtonWClass = 0x27548EC9U,
|
||||
WC_PNIHiddenWnd = 0xF53ADFC1U,
|
||||
WC_DLGBOX = 0x5D3AD0ABU, // #32770 WC_DIALOG
|
||||
/////////////
|
||||
WC_SHELLDLL_DefView = 0xB434F7C2, //L"SHELLDLL_DefView"
|
||||
WC_SysTreeView32 = 0x84265DD4, //L"SysTreeView32" 49431
|
||||
WC_CabinetWClass = 0xA26CA168, //L"CabinetWClass" 49772
|
||||
WC_ExplorerWClass = 0x891808A3, //L"ExplorerWClass"
|
||||
WC_SysListView32 = 0xB9B50F60, //L"SysListView32" 49414
|
||||
WC_NamespaceTreeControl = 0x4683C2C3, //L"NamespaceTreeControl"
|
||||
WC_ApplicationManager = 0x9C10E7BD,//L"ApplicationManager_DesktopShellWindow"
|
||||
WC_ShellTabWindowClass = 0x7B66A982U,//ShellTabWindowClass
|
||||
//Windows 11
|
||||
WC_Windows_UI_Composition_DesktopWindowContentBridge = 0x8122A1C6U, //Windows.UI.Composition.DesktopWindowContentBridge 49992
|
||||
WC_WINDOWS_UI_INPUT_INPUTSITE_WINDOWCLASS = 0x86865AE9U, //Windows.UI.Input.InputSite.WindowClass
|
||||
WC_XAML_WINDOWEDPOPUPCLASS = 0x8CB7F0C1U, // Xaml_WindowedPopupClas
|
||||
// UI
|
||||
WC_DirectUIHWND = 0x43F2554FU,
|
||||
WC_DUIViewWndClassName = 0xCD1A7C82U,
|
||||
WC_ReBarWindow32 = 0xF75EE10EU,
|
||||
WC_TravelBand = 0xDD9E6528U,
|
||||
// block window
|
||||
WC_BLOCK_IDM_DOWNLOAD_BUTTON_CLASS = 0xC4A83BC9U,
|
||||
WC_MSTASKSWWCLASS = 0x2C50536FU,
|
||||
WC_TRAYNOTIFYWND = WC_TrayNotifyWnd
|
||||
};
|
||||
//DirectUIHWND
|
||||
//DUIViewWndClassName
|
||||
//ShellTabWindowClass
|
||||
enum class SelectionMode : int8_t
|
||||
{
|
||||
None,
|
||||
Single,
|
||||
MultiUnique,
|
||||
MultiSingle,
|
||||
Multiple
|
||||
};
|
||||
|
||||
enum WINDOW_tag : int32_t
|
||||
{
|
||||
WINDOW_NONE,
|
||||
WINDOW_UI,
|
||||
WINDOW_SYSMENU,
|
||||
WINDOW_EDIT,
|
||||
WINDOW_START,
|
||||
WINDOW_TASKBAR,
|
||||
WINDOW_DESKTOP,
|
||||
WINDOW_EXPLORER,
|
||||
WINDOW_EXPLORER_TREE,
|
||||
WINDOW_COMPUTER,
|
||||
WINDOW_RECYCLEBIN,
|
||||
WINDOW_LIBRARIES,
|
||||
WINDOW_HOME,
|
||||
WINDOW_QUICK_ACCESS
|
||||
};
|
||||
|
||||
struct WINDOW
|
||||
{
|
||||
HMODULE hInstance{};
|
||||
Windows::Window handle{};
|
||||
uint32_t hash = 0;
|
||||
uint32_t id = 0;
|
||||
uint32_t parent = 0;
|
||||
uint32_t front = 0;
|
||||
bool desktop{};
|
||||
bool explorer{};
|
||||
bool explorer_tree{};
|
||||
bool application{};
|
||||
bool has_IShellBrowser{};
|
||||
|
||||
void copy(const WINDOW &src)
|
||||
{
|
||||
::memcpy(this, &src, sizeof(src));
|
||||
}
|
||||
|
||||
bool isTaskbar() const
|
||||
{
|
||||
return id == WINDOW_TASKBAR;
|
||||
}
|
||||
};
|
||||
|
||||
class Selections
|
||||
{
|
||||
public:
|
||||
struct PathItem
|
||||
{
|
||||
PathType Type;
|
||||
PathType Group;
|
||||
string Path;
|
||||
string Raw;
|
||||
string Name;
|
||||
string Title;
|
||||
string Extension;
|
||||
bool ReadOnly = false;
|
||||
bool Hidden = false;
|
||||
bool IsLink = false;
|
||||
|
||||
PathItem() noexcept
|
||||
: Type{ PathType::Unknown }, Group{ PathType::Unknown }
|
||||
{
|
||||
}
|
||||
|
||||
PathItem(const string &path, const string &pathRaw, bool readOnly, bool hidden)
|
||||
: Path{ path }, Raw{ pathRaw }, Type{ PathType::Unknown }, Group{ PathType::Unknown },
|
||||
ReadOnly{ readOnly }, Hidden{ hidden }
|
||||
{
|
||||
if(!path.empty())
|
||||
{
|
||||
Name = Path::Name(path).move();
|
||||
Title = Path::Title(path).move();
|
||||
}
|
||||
}
|
||||
|
||||
PathItem(PathType const &type, PathType const &groupType, const string &path = nullptr)
|
||||
: Path{ path }, Type{ type }, Group{ groupType }
|
||||
{
|
||||
if(!path.empty())
|
||||
{
|
||||
Name = Path::Name(path).move();
|
||||
Title = Path::Title(Name).move();
|
||||
}
|
||||
}
|
||||
|
||||
~PathItem() {}
|
||||
|
||||
string get(const string "e = nullptr, const wchar_t* sep = nullptr) const
|
||||
{
|
||||
string result = Path;
|
||||
if(sep) result.replace(L"\\", sep);
|
||||
return !quote.empty() ? Quote(result, quote).move() : result.move();
|
||||
}
|
||||
|
||||
string get_raw(const string "e) const
|
||||
{
|
||||
return !quote.empty() ? Quote(Raw).move() : Raw;
|
||||
}
|
||||
|
||||
string get_name(const string "e) const
|
||||
{
|
||||
return !quote.empty() ? Quote(Name).move() : Name;
|
||||
}
|
||||
|
||||
string get_title(const string "e) const
|
||||
{
|
||||
return !quote.empty() ? Quote(Title).move() : Title;
|
||||
}
|
||||
|
||||
string get_extension(const string "e) const
|
||||
{
|
||||
return !quote.empty() ? Quote(Extension).move() : Extension;
|
||||
}
|
||||
|
||||
bool IsDesktop() const { return this->Type == PathType::Desktop; }
|
||||
bool IsFile() const { return this->Group == PathType::File; }
|
||||
bool IsRoot() const { return this->Type == IO::PathType::Drive; }
|
||||
bool IsDirectory() const { return this->Group == PathType::Directory; }
|
||||
bool IsNamespace() const { return this->Group == PathType::Namespace; }
|
||||
bool IsDVD() const { return this->Type == PathType::DVD; }
|
||||
bool IsUSB() const { return this->Type == PathType::USB; }
|
||||
bool IsFixed() const { return this->Type == PathType::Fixed; }
|
||||
bool IsVHD() const { return this->Type == PathType::VHD; }
|
||||
bool IsRemovable() const { return this->Type == PathType::Removable; }
|
||||
};
|
||||
|
||||
const wchar_t *Empty = L"";
|
||||
|
||||
std::vector<PathItem*> Items;
|
||||
|
||||
PathItem *Front{};
|
||||
string Parent;
|
||||
string ParentRaw;
|
||||
string Directory;
|
||||
SelectionMode Mode = SelectionMode::None;
|
||||
size_t Index = 0U;
|
||||
int32_t Types[FSO_MAX]{ };
|
||||
int32_t front = -1;
|
||||
bool Background{};
|
||||
WINDOW Window{};
|
||||
bool destroy = true;
|
||||
IShellBrowser* ShellBrowser{};
|
||||
|
||||
IShellView *ShellView{};
|
||||
IFolderView2 *FolderView{};
|
||||
|
||||
struct
|
||||
{
|
||||
bool explorer{};
|
||||
bool taskbar{};
|
||||
bool apps{};
|
||||
bool contextmenuhandler{};
|
||||
}loader;
|
||||
|
||||
struct {
|
||||
uint32_t FILE = 0;
|
||||
uint32_t DIRECTORY = 0;
|
||||
uint32_t DRIVE = 0;
|
||||
uint32_t NAMESPACE = 0;
|
||||
uint32_t operator()() const { return FILE + DIRECTORY + DRIVE + NAMESPACE; }
|
||||
}count{};
|
||||
|
||||
private:
|
||||
uint32_t _first_extension = 0U;
|
||||
uint32_t _multi_extension = 0U;
|
||||
|
||||
public:
|
||||
Selections(HWND handle = nullptr)
|
||||
{
|
||||
Window.handle = handle;
|
||||
}
|
||||
|
||||
// destructor cleans up all resources
|
||||
~Selections()
|
||||
{
|
||||
this->Clear();
|
||||
|
||||
//if(ShellBrowser)
|
||||
// ShellBrowser->Release();
|
||||
|
||||
if(ShellView)
|
||||
ShellView->Release();
|
||||
|
||||
if(FolderView)
|
||||
FolderView->Release();
|
||||
|
||||
ShellBrowser = {};
|
||||
ShellView = {};
|
||||
FolderView = {};
|
||||
}
|
||||
|
||||
Selections(const Selections &other) = delete;
|
||||
Selections &operator=(const Selections &other) = delete;
|
||||
|
||||
void Clear();
|
||||
void Add(PathItem *pathItem);
|
||||
void Add(PathType const &pathType, PathType const &groupType, const string &name);
|
||||
|
||||
PathItem *Get(size_t index);
|
||||
PathType Type(size_t index = 0);
|
||||
PathType GroupType(size_t index);
|
||||
string Path(size_t index, const string "e = nullptr);
|
||||
string Path(const string "e = nullptr);
|
||||
string Root(size_t index = 0);
|
||||
|
||||
string ShortPath(size_t index = 0);
|
||||
|
||||
string Name(size_t index = 0);
|
||||
string Extension(size_t index = 0);
|
||||
string FileNameWithoutExtension(size_t index = 0);
|
||||
|
||||
string Sel(const string "e, const wchar_t *sep = SEP_SPACE, const wchar_t *path_sep = nullptr);
|
||||
string FilesName(const string "e = nullptr, const wchar_t *sep = SEP_SPACE);
|
||||
string GetFilesExtension(const string "e = nullptr, const wchar_t *sep = SEP_SPACE);
|
||||
string FilesNameWithoutExtension(const string "e = nullptr, const wchar_t *sep = SEP_SPACE);
|
||||
string SelNamespaces(const string "e, const wchar_t *sep = SEP_SPACE);
|
||||
string SelFiles(const string "e = nullptr, const wchar_t *sep = SEP_SPACE);
|
||||
string DiresName(const string "e, const wchar_t *sep = SEP_SPACE);
|
||||
string SelDirs(const string "e, const wchar_t *sep = SEP_SPACE);
|
||||
string SelDrives(const wchar_t *sep = SEP_SPACE);
|
||||
string ShortPaths(const wchar_t *sep = SEP_SPACE);
|
||||
string PathsName(const string "e = nullptr, const wchar_t *sep = SEP_SPACE);
|
||||
|
||||
bool is_back(int type = -1) const;
|
||||
/*bool is_back_root() const;
|
||||
bool is_back_directory() const;
|
||||
bool is_back_namespace() const;
|
||||
bool is_back_desktop() const;*/
|
||||
bool is_taskbar() const;
|
||||
bool is_desktop_window() const;
|
||||
|
||||
bool verify_mode(SelectionMode mode);
|
||||
bool verify_types(const FileSystemObjects &fso) const;
|
||||
|
||||
void QuerySelectionMode();
|
||||
bool QueryShellWindow();
|
||||
bool QuerySelected();
|
||||
bool Preparing();
|
||||
bool Parse(IShellItem *shellItem);
|
||||
bool Parse(FileProperties *prop);
|
||||
auto Count() const {return Items.size(); };
|
||||
|
||||
private:
|
||||
static constexpr const wchar_t *SEP_SPACE = L" ";
|
||||
|
||||
static const SFGAOF FGAOF_DEF =
|
||||
SFGAO_FOLDER | SFGAO_FILESYSTEM | SFGAO_FILESYSANCESTOR |
|
||||
SFGAO_REMOVABLE | SFGAO_STREAM | SFGAO_LINK |
|
||||
SFGAO_DROPTARGET | SFGAO_HASSTORAGE | SFGAO_CANMONIKER | SFGAO_READONLY | SFGAO_HIDDEN;
|
||||
|
||||
public:
|
||||
static string Quote(const string &str, const string "e = L"\"")
|
||||
{
|
||||
return (quote + str + quote).move();
|
||||
}
|
||||
|
||||
static bool GetFileProperties(IShellItem *shellItem, FileProperties *prop);
|
||||
inline static Point point = {};
|
||||
static constexpr auto GUID_HOME = 0xA8A544D5U; //::{F874310E-B6B7-47DC-BC84-B9E6B38F5903}
|
||||
static constexpr auto GUID_QUICK_ACCESS = 0x214BFAA6U; //::{031E4825-7B94-4DC3-B131-E946B44C8DD5}
|
||||
static constexpr auto GUID_LIBRARIES = 0xDB6BDBF5U; //::{679F85CB-0220-4080-B29B-5540CC05AAB6}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,32 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
/*class Styles
|
||||
{
|
||||
public:
|
||||
bool Enable = false;
|
||||
|
||||
int MaxHeight = -1;
|
||||
int MaxWidth = -1;
|
||||
int MinHeight = -1;
|
||||
int MinWidth = -1;
|
||||
int Height = -1;
|
||||
int Width = -1;
|
||||
|
||||
COLORREF FontColor = 0;
|
||||
COLORREF FontSelColor = 0;
|
||||
COLORREF BackColor = 0;
|
||||
COLORREF BackSelColor = 0;
|
||||
|
||||
int FontSize = -1;
|
||||
int FontWeight = 0;//0 normal, 2 bold
|
||||
int FontStyle = 0; //0 normal, 1 italic, 2 oblique
|
||||
|
||||
int TextAlign = 0; // 0 left, 1 right, 2 center
|
||||
|
||||
};*/
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,953 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
struct DPI
|
||||
{
|
||||
uint32_t org = 96;
|
||||
uint32_t val = 96;
|
||||
|
||||
//scale factor
|
||||
double scale() const { return double(val) / double(org); }
|
||||
|
||||
bool scaled() const { return val != org; }
|
||||
|
||||
template<typename T = long>
|
||||
T operator()(auto val) const { return value<T>(val); }
|
||||
|
||||
template<typename T = long>
|
||||
T value(auto val) const { return static_cast<T>(std::rint(val * double(this->val) / 96.0)); }
|
||||
|
||||
template<typename T = long>
|
||||
T valuexx(auto val) const { return static_cast<T>(val * double(this->val) / 96.0); }
|
||||
|
||||
template<typename T = long>
|
||||
T original(auto value) const { return static_cast<T>(std::floor(value * double(org) / 96.0)); }
|
||||
|
||||
long value2(auto value) const
|
||||
{
|
||||
return static_cast<long>(std::rint(value * double(this->val) / double(org)));
|
||||
}
|
||||
/*template<typename T = long>
|
||||
float dpif(T value) const { return float((value * _dpi) / 96.0); }
|
||||
double dpi() const { return double(_dpi) / 96.0; }
|
||||
*/
|
||||
|
||||
long scaleFactor() const { return long((val / 96.0) * 100.0); }
|
||||
|
||||
template<typename T = long>
|
||||
static T Value(auto val, double dpi = 96.0) { return static_cast<T>(std::rint(val * dpi / 96.0)); }
|
||||
};
|
||||
|
||||
//typedef IMMERSIVE_COLOR_NAMED_TYPES *(WINAPI *pGetImmersiveColorNamedTypeByIndex)(unsigned dwImmersiveColorType); //#100
|
||||
enum class Immersive_Color : uint32_t
|
||||
{
|
||||
SystemAccentLight3 = 1,
|
||||
SystemAccentLight2,
|
||||
SystemAccentLight1,
|
||||
SystemAccent,
|
||||
SystemAccentDark1,
|
||||
SystemAccentDark2,
|
||||
SystemAccentDark3,
|
||||
};
|
||||
|
||||
class ImmersiveColor
|
||||
{
|
||||
inline static HMODULE hUxTheme = ::GetModuleHandleW(L"uxtheme.dll");
|
||||
public:
|
||||
static uint32_t GetColorByColorType(uint32_t colorType);
|
||||
static uint32_t GetColorByName(const wchar_t *name);
|
||||
static uint32_t GetImmersiveUserColorSetPreference(bool bForceCheckRegistry, bool bSkipCheckOnFail);
|
||||
static uint32_t GetImmersiveColorFromColorSetEx(uint32_t dwImmersiveColorSet, uint32_t dwImmersiveColorType, bool bIgnoreHighContrast, uint32_t dwHighContrastCacheMode);
|
||||
static uint32_t GetImmersiveColorTypeFromName(const wchar_t *name);
|
||||
static uint32_t GetImmersiveColorSetCount();
|
||||
static bool IsSupported();
|
||||
};
|
||||
|
||||
struct VIEWMODE
|
||||
{
|
||||
static const int8_t AUTO = -1;
|
||||
static const int8_t COMPACT = 0;
|
||||
static const int8_t SMALL = 2;
|
||||
static const int8_t MEDIUM = 4;
|
||||
static const int8_t LARGE = 8;
|
||||
static const int8_t WIDE = 10;
|
||||
|
||||
static auto get(int8_t view)
|
||||
{
|
||||
switch(view)
|
||||
{
|
||||
case AUTO: return -1;
|
||||
case COMPACT: return 0;
|
||||
case SMALL: return 2;
|
||||
case MEDIUM: return 4;
|
||||
case LARGE: return 8;
|
||||
case WIDE: return 10;
|
||||
default: return view < -1 ? -1 : view > 48 ? 48 : view;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
enum class ThemeType:uint8_t
|
||||
{
|
||||
Auto,
|
||||
System,
|
||||
HighContrast,
|
||||
White,
|
||||
Black,
|
||||
Classic,
|
||||
Edge,
|
||||
Dark,
|
||||
Light,
|
||||
Modern,
|
||||
Custom
|
||||
};
|
||||
|
||||
struct Theme
|
||||
{
|
||||
inline static auto ver = Windows::Version::Instance();
|
||||
static const auto RADIUS = 8;
|
||||
|
||||
struct color_t
|
||||
{
|
||||
Color text;
|
||||
Color back;
|
||||
};
|
||||
|
||||
struct state_t
|
||||
{
|
||||
Color nor;
|
||||
Color sel;
|
||||
Color nor_dis;
|
||||
Color sel_dis;
|
||||
};
|
||||
|
||||
struct gradientstop_t
|
||||
{
|
||||
double offset{};
|
||||
Color color;
|
||||
};
|
||||
|
||||
struct {
|
||||
bool enabled{};
|
||||
double linear[5]{};
|
||||
double radial[6]{};
|
||||
std::vector<gradientstop_t> stpos;
|
||||
}gradient;
|
||||
|
||||
struct {
|
||||
Color color;
|
||||
uint8_t opacity = 0xFF;
|
||||
int8_t effect = 0;
|
||||
Color tintcolor;
|
||||
string image;
|
||||
} background;
|
||||
|
||||
struct
|
||||
{
|
||||
Color color;
|
||||
uint8_t size{};
|
||||
uint8_t radius{};
|
||||
Margin padding;
|
||||
}border;
|
||||
|
||||
struct {
|
||||
Color color = 0xFF000000;
|
||||
uint8_t size = 3;
|
||||
uint8_t offset = 2;
|
||||
bool enabled = true;
|
||||
} shadow;
|
||||
|
||||
struct
|
||||
{
|
||||
state_t color;
|
||||
long size{};
|
||||
int8_t tap = -1;
|
||||
int8_t alig = -1;
|
||||
uint32_t prefix = 0xFFFFFFFF;
|
||||
string name;
|
||||
} text;
|
||||
|
||||
struct
|
||||
{
|
||||
state_t color;
|
||||
uint8_t opacity = 0xFF;
|
||||
state_t border;
|
||||
uint8_t radius{};
|
||||
Margin padding;
|
||||
Margin margin;
|
||||
long height() const { return padding.height() + margin.height(); }
|
||||
long width() const { return padding.width() + margin.width(); }
|
||||
} back;
|
||||
|
||||
struct
|
||||
{
|
||||
Color color;
|
||||
uint8_t size{};
|
||||
Margin margin;
|
||||
} separator;
|
||||
|
||||
struct
|
||||
{
|
||||
state_t chevron;
|
||||
state_t checked;
|
||||
state_t bullet;
|
||||
}symbols;
|
||||
|
||||
struct {
|
||||
uint32_t min_width = 0u;
|
||||
uint32_t max_width = 0u;
|
||||
int8_t rtl = 0;
|
||||
struct {
|
||||
int8_t align = 0x7F;
|
||||
}popup;
|
||||
}layout;
|
||||
|
||||
struct {
|
||||
string font;
|
||||
bool enabled = true;
|
||||
} glyph;
|
||||
|
||||
struct {
|
||||
Color color[3];
|
||||
uint32_t size = 16;
|
||||
uint8_t gap{};
|
||||
bool scale = true;
|
||||
bool enabled = true;
|
||||
int display{};
|
||||
}image;
|
||||
|
||||
struct
|
||||
{
|
||||
uint8_t radius{};
|
||||
uint8_t opacity = 0xFF;
|
||||
uint16_t time = 1000;
|
||||
uint16_t maxwidth = 2000;
|
||||
Margin padding;
|
||||
Color border;
|
||||
color_t normal;
|
||||
color_t primary;
|
||||
color_t success;
|
||||
color_t info;
|
||||
color_t warning;
|
||||
color_t danger;
|
||||
}
|
||||
tip;
|
||||
|
||||
DPI *dpi{};
|
||||
|
||||
ThemeType Type = ThemeType::Auto;
|
||||
uint8_t mode{}; //0 = light, 1 = dark, 2= high contrast
|
||||
bool transparent = true;
|
||||
//int view = -1;
|
||||
int view2 = 0;
|
||||
LOGFONTW font{};
|
||||
|
||||
bool enableTransparency{};
|
||||
bool systemUsesLightTheme = true;
|
||||
bool appsUseLightTheme = true;
|
||||
bool isHighContrast{};
|
||||
|
||||
struct {
|
||||
uint8_t mode{};
|
||||
bool transparency{};
|
||||
}system;
|
||||
|
||||
static const Color& get_color(const state_t &state, bool selected = false, bool disabled = false)
|
||||
{
|
||||
if(selected)
|
||||
return disabled ? state.sel_dis : state.sel;
|
||||
return disabled ? state.nor_dis : state.nor;
|
||||
}
|
||||
|
||||
void set_symbols_as_text(bool mode)
|
||||
{
|
||||
symbols.checked = { text.color.nor, text.color.sel, text.color.nor_dis, text.color.sel_dis };
|
||||
symbols.bullet = { text.color.nor, text.color.sel, text.color.nor_dis, text.color.sel_dis };
|
||||
symbols.chevron = { text.color.nor, text.color.sel, text.color.nor_dis, text.color.sel_dis };
|
||||
|
||||
tip.normal = { text.color.nor, background.color };
|
||||
tip.normal.back.a = 0xff;
|
||||
|
||||
if(mode)
|
||||
{
|
||||
//tip.danger = { 0xFF000000, 0xFFDDDDFF };
|
||||
//tip.warning = { 0xFF000000, 0xFFAAFFFF };
|
||||
//tip.info = { 0xFF000000, 0xFFFFFFDD };
|
||||
tip.primary = { 0xFFFFFFFF, 0xFF713C26 };
|
||||
tip.info = { 0xFFFFFFFF, 0xFF572C39 };
|
||||
tip.success = { 0xFFFFFFFF, 0xFF194B28 };
|
||||
tip.warning = { 0xFFFFFFFF, 0xFF1B4E61 };
|
||||
tip.danger = { 0xFFFFFFFF, 0xFF051053 };
|
||||
}
|
||||
else
|
||||
{
|
||||
tip.primary = { 0xFF000000, 0xFFF7E9DE };
|
||||
tip.info = { 0xFF000000, 0xFFFCD8E9 };
|
||||
tip.success = { 0xFF000000, 0xFFDEF6E6 };
|
||||
tip.warning = { 0xFF000000, 0xFFD0F6FB };
|
||||
tip.danger = { 0xFF000000, 0xFFE9E8F6 };
|
||||
}
|
||||
}
|
||||
|
||||
void scale()
|
||||
{
|
||||
if(!dpi)
|
||||
return;
|
||||
|
||||
auto ev = [&](Margin &m)
|
||||
{
|
||||
m.left = dpi->value(m.left);
|
||||
m.top = dpi->value(m.top);
|
||||
m.right = dpi->value(m.right);
|
||||
m.bottom = dpi->value(m.bottom);
|
||||
};
|
||||
|
||||
text.size = dpi->value<uint8_t>(text.size);
|
||||
|
||||
if(text.tap > 0)
|
||||
text.tap = dpi->value<int8_t>(text.tap);
|
||||
|
||||
back.radius = dpi->value<uint8_t>(back.radius);
|
||||
ev(back.margin);
|
||||
ev(back.padding);
|
||||
|
||||
border.size = dpi->value<uint8_t>(border.size);
|
||||
border.radius = dpi->value<uint8_t>(border.radius);
|
||||
ev(border.padding);
|
||||
|
||||
separator.size = dpi->value<uint8_t>(separator.size);
|
||||
ev(separator.margin);
|
||||
|
||||
shadow.size = dpi->value<uint8_t>(shadow.size);
|
||||
shadow.offset = dpi->value<uint8_t>(shadow.offset);
|
||||
|
||||
image.size = dpi->value<uint32_t>(image.size);
|
||||
image.gap = dpi->value<uint8_t>(image.gap);
|
||||
|
||||
if(layout.popup.align != 0x7F)
|
||||
layout.popup.align = dpi->value<int8_t>(layout.popup.align);
|
||||
|
||||
if(layout.min_width > 0)
|
||||
layout.min_width = dpi->value<long>(layout.min_width);
|
||||
|
||||
if(layout.max_width > 0)
|
||||
layout.max_width = dpi->value<long>(layout.max_width);
|
||||
}
|
||||
|
||||
static uint8_t radius(uint8_t value)
|
||||
{
|
||||
switch(value)
|
||||
{
|
||||
case 0: return 0;
|
||||
case 1: return 4;
|
||||
case 2: return 8;
|
||||
case 3: return 12;
|
||||
case 4: return 16;
|
||||
}
|
||||
return 4;
|
||||
}
|
||||
|
||||
static uint8_t opacity(uint8_t percent) { return (percent * 255) / 100; }
|
||||
|
||||
//template<typename T=long>
|
||||
//T dpi(auto value) const { return DPI<T>(value, _dpi); }
|
||||
|
||||
static auto pow(auto v) { return v + v; }
|
||||
|
||||
static Theme Default(auto type = ThemeType::System, uint8_t mode = 0)
|
||||
{
|
||||
Theme th;
|
||||
th.mode = mode;
|
||||
th.Type = type;
|
||||
th.background.color.from(::GetSysColor(COLOR_MENU), 100);
|
||||
th.border.color.from(::GetSysColor(COLOR_WINDOWFRAME), 50);
|
||||
th.border.radius = 0;
|
||||
th.border.size = 1;
|
||||
th.border.padding = { 0, 4, 0, 4 };
|
||||
th.shadow.color.opacity(25);
|
||||
|
||||
th.separator.color = th.border.color;
|
||||
th.separator.color.opacity(100);
|
||||
th.separator.size = 1;
|
||||
th.separator.margin = { 8, 3, 8, 3 };
|
||||
|
||||
th.text.size = 12;
|
||||
th.text.tap = 12;
|
||||
|
||||
th.text.color = {
|
||||
Color(::GetSysColor(COLOR_MENUTEXT), 0xFF),
|
||||
Color(::GetSysColor(COLOR_MENUTEXT), 0xFF),
|
||||
Color(::GetSysColor(COLOR_GRAYTEXT), 0xFF),
|
||||
Color(::GetSysColor(COLOR_GRAYTEXT), 0xFF)
|
||||
};
|
||||
|
||||
th.back.color = {
|
||||
th.background.color,
|
||||
Color(::GetSysColor(COLOR_HIGHLIGHT), 0xFF),
|
||||
th.background.color,
|
||||
th.background.color
|
||||
};
|
||||
|
||||
//th.back.border = th.back.color.sel;
|
||||
th.back.padding = { 10, 3, 10, 3 };
|
||||
th.back.margin = { 4, 0, 4, 0 };
|
||||
th.back.radius = 0;
|
||||
|
||||
th.set_symbols_as_text(0);
|
||||
|
||||
th.image.size = 16;
|
||||
th.image.gap = 10;
|
||||
|
||||
if(mode == 1)
|
||||
{
|
||||
th.image.color[0] = Color::Swap(0xFFE0DFDF);
|
||||
th.image.color[1] = Color::Swap(0xFF4CC2FF);
|
||||
th.image.color[2] = Color::Swap(0x00000000);
|
||||
}
|
||||
else
|
||||
{
|
||||
th.image.color[0] = Color::Swap(0xFF555555);
|
||||
th.image.color[1] = Color::Swap(0xFF0078D4);
|
||||
th.image.color[2] = Color::Swap(0xFFFAFAFA);
|
||||
}
|
||||
|
||||
th.tip.padding = {10, 10, 10, 10};
|
||||
th.tip.maxwidth = 640;
|
||||
th.tip.opacity = 0xff;
|
||||
th.tip.time = 1000;
|
||||
th.tip.normal = { th.text.color.nor, th.background.color };
|
||||
th.tip.normal.back.a = 0xff;
|
||||
|
||||
//th.tip.error = { 0xFF000000, Color::Swap(0xFFDDDDFF) };
|
||||
//th.tip.warning = { 0xFF000000, Color::Swap(0xFFAAFFFF) };
|
||||
//th.tip.info = { 0xFF000000, Color::Swap(0xFFFFFFDD) };
|
||||
|
||||
return th;
|
||||
}
|
||||
|
||||
static auto HighContrast()
|
||||
{
|
||||
auto th = Default(ThemeType::HighContrast, 2);
|
||||
|
||||
th.background.color = Color(::GetSysColor(COLOR_WINDOW), 0xFF);
|
||||
if(Windows::Version::Instance().IsWindows11OrGreater())
|
||||
{
|
||||
th.border.radius = 8;
|
||||
th.back.margin = { 4, 4, 4, 4 };
|
||||
th.back.radius = 4;
|
||||
th.tip.radius = 4;
|
||||
}
|
||||
|
||||
th.shadow.color.opacity(25);
|
||||
th.separator.margin = { 0, 3, 0, 3 };
|
||||
|
||||
th.text.size = 12;
|
||||
//COLOR_BTNTEXT
|
||||
th.text.color = {
|
||||
Color(::GetSysColor(COLOR_WINDOWTEXT), 0xFF),
|
||||
Color(::GetSysColor(COLOR_HIGHLIGHTTEXT), 0xFF),
|
||||
Color(::GetSysColor(COLOR_GRAYTEXT), 0xFF),
|
||||
Color(::GetSysColor(COLOR_GRAYTEXT), 0xFF)
|
||||
};
|
||||
|
||||
th.back.color = {
|
||||
th.background.color,
|
||||
Color(::GetSysColor(COLOR_HIGHLIGHT), 0xFF),
|
||||
th.background.color,
|
||||
th.background.color,
|
||||
};
|
||||
|
||||
// th.back.border = th.back.color.sel;
|
||||
// th.block.margin = { 0, 4 };
|
||||
|
||||
th.set_symbols_as_text(false);
|
||||
|
||||
return th;
|
||||
}
|
||||
|
||||
static auto System()
|
||||
{
|
||||
auto th= Default(ThemeType::System, 0);
|
||||
th.set_symbols_as_text(0);
|
||||
|
||||
return th;
|
||||
}
|
||||
|
||||
static auto Modern(auto type = ThemeType::Light, uint8_t mode = 0, uint8_t enableTransparency = 0)
|
||||
{
|
||||
auto th = Default(type, mode);
|
||||
|
||||
th.border.radius = 8;
|
||||
th.border.size = 0;
|
||||
th.border.padding = { 0, 4, 0, 4 };
|
||||
th.separator.size = 1;
|
||||
th.separator.margin = { 0, 4, 0, 4 };
|
||||
th.text.size = 14;
|
||||
th.back.padding = { 10, 4, 10, 4 };
|
||||
th.back.margin = { 4, 0, 4, 0 };
|
||||
th.back.radius = 4;
|
||||
th.font.lfHeight = 14;
|
||||
|
||||
th.tip.padding = { 10,10,10,10 };
|
||||
th.tip.radius = 4;
|
||||
|
||||
th.border.color.opacity(10);
|
||||
|
||||
th.shadow.size = 3;
|
||||
th.shadow.offset = 2;
|
||||
th.shadow.color = 0x80000000;
|
||||
|
||||
if(mode)
|
||||
{
|
||||
th.shadow.color.a = 0x20;
|
||||
th.border.color = 0xFF2C2C2C;
|
||||
th.background.color = 0xFF2C2C2C;
|
||||
//th.text.color = { 0xFFFFFFFF, 0xFFFFFFFF, 0xFF6D6D6D, 0xFF6D6D6D };
|
||||
th.text.color = { 0xFFFFFFFF, 0xFFFFFFFF, 0x80FFFFFF, 0x80FFFFFF };
|
||||
|
||||
if(enableTransparency)
|
||||
{
|
||||
th.border.size = 1;
|
||||
th.border.color = th.background.color;
|
||||
th.border.color.a = 0x40;
|
||||
th.background.color.a = 0x00;
|
||||
th.background.tintcolor = th.background.color;
|
||||
th.background.tintcolor.a = 0x40;
|
||||
th.back.color = { 0x00000000, 0x10FFFFFF, 0x00000000, 0x05FFFFFF };
|
||||
th.separator.color = 0x15FFFFFF;
|
||||
}
|
||||
else
|
||||
{
|
||||
th.separator.color = 0xFF3D3D3D;
|
||||
th.back.color = { 0xFF2C2C2C, 0xFF383838, 0xFF2C2C2C, 0xFF2C2C2C };
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
th.shadow.color.a = 0x10;
|
||||
th.border.color = 0xFFF9F9F9;
|
||||
th.separator.color = 0xFFEAEAEA;
|
||||
//th.text.color = { 0xFF000000, 0xFF000000, 0xFF9F9F9F, 0xFF9F9F9F };
|
||||
th.text.color = { 0xFF000000, 0xFF000000, 0x80000000, 0x80000000 };
|
||||
|
||||
if(enableTransparency)
|
||||
{
|
||||
th.background.color.a = 0x00;
|
||||
th.background.tintcolor = th.background.color;
|
||||
th.background.tintcolor.a = 0xCF;
|
||||
th.back.color = { 0x00000000, 0x08000000, 0x00000000, 0x05000000 };
|
||||
th.separator.color = 0x15000000;
|
||||
}
|
||||
else
|
||||
{
|
||||
th.background.color = 0xFFF9F9F9;
|
||||
th.back.color = { 0xFFF9F9F9, 0xFFF0F0F0, 0xFFF9F9F9, 0xFFF9F9F9 };
|
||||
}
|
||||
}
|
||||
|
||||
th.set_symbols_as_text(mode);
|
||||
// th.back.border.nor = th.back.color.nor;
|
||||
//th.border.color.opacity(10);
|
||||
return th;
|
||||
}
|
||||
|
||||
static auto Light(bool modern = true, uint8_t enableTransparency = 0)
|
||||
{
|
||||
auto th = Default(ThemeType::Light, 0);
|
||||
auto isw11 = Windows::Version::Instance().IsWindows11OrGreater();
|
||||
|
||||
if(modern)
|
||||
{
|
||||
th = Modern(ThemeType::Light, 0, enableTransparency);
|
||||
}
|
||||
else if(isw11)
|
||||
{
|
||||
th.separator.color = 0xFFD7D7D7;
|
||||
th.border.color = 0xFFE5E5E5;
|
||||
th.background.color = 0xFFF9F9F9;
|
||||
th.text.color = { 0xFF000000, 0xFFFFFFFF, 0xFF9F9F9F, 0xFF9F9F9F };
|
||||
th.back.color = { 0xFFF9F9F9, Color::Swap(0xFF0078D4), 0xFFF9F9F9, 0xFFF0F0F0 };
|
||||
|
||||
th.border.padding.left = 4;
|
||||
th.border.padding.right = 4;
|
||||
th.border.radius = th.radius(2);
|
||||
th.back.radius = th.radius(1);
|
||||
th.back.padding.top = 0;
|
||||
th.back.padding.bottom = 0;
|
||||
th.back.margin = { 0, 4, 0, 4 };
|
||||
th.shadow.size = 3;
|
||||
|
||||
if(enableTransparency)
|
||||
{
|
||||
th.border.size = 1;
|
||||
th.border.color = th.background.color;
|
||||
th.border.color.a = 0x40;
|
||||
th.background.color.a = 0x00;
|
||||
th.background.tintcolor = th.background.color;
|
||||
th.background.tintcolor.a = 0x40;
|
||||
th.back.color.nor = 0x00000000;
|
||||
th.back.color.nor_dis = 0x00000000;
|
||||
th.back.color.sel.a = 0xaa;
|
||||
th.back.color.sel_dis.a = 0x80;
|
||||
th.separator.color = 0x15FFFFFF;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if(enableTransparency)
|
||||
{
|
||||
th.background.color.a = 0x00;
|
||||
th.background.tintcolor = th.background.color;
|
||||
th.background.tintcolor.a = 0xCF;
|
||||
th.back.color = { 0x00000000, 0x08000000, 0x00000000, 0x05000000 };
|
||||
th.separator.color = 0x15000000;
|
||||
}
|
||||
else
|
||||
{
|
||||
th.background.color = 0xFFF9F9F9;
|
||||
th.back.color = { 0xFFF9F9F9, 0xFFF0F0F0, 0xFFF9F9F9, 0xFFF9F9F9 };
|
||||
}
|
||||
}
|
||||
|
||||
th.shadow.color.a = 0x10;
|
||||
//th.back.border = th.back.color.nor;
|
||||
th.set_symbols_as_text(0);
|
||||
return th;
|
||||
}
|
||||
|
||||
static auto Dark(bool modern = true, uint8_t enableTransparency = 0)
|
||||
{
|
||||
auto th = Default(ThemeType::Dark, 1);
|
||||
auto isw11 = Windows::Version::Instance().IsWindows11OrGreater();
|
||||
th.border.color.opacity(100);
|
||||
if(modern)
|
||||
{
|
||||
th = Modern(ThemeType::Dark, 1, enableTransparency);
|
||||
if(!enableTransparency)
|
||||
{
|
||||
th.border.color.opacity(10);
|
||||
th.background.color = 0xFF2C2C2C;
|
||||
th.separator.color = 0xFF3D3D3D;
|
||||
th.text.color = { 0xFFFFFFFF, 0xFFFFFFFF, 0xFF6D6D6D, 0xFF6D6D6D };
|
||||
th.back.color = { 0xFF2C2C2C, 0xFF383838, 0xFF2C2C2C, 0xFF2C2C2C };
|
||||
}
|
||||
}
|
||||
else if(isw11)
|
||||
{
|
||||
th.separator.color = 0xFF3E3E3E;
|
||||
th.border.color = 0xFF3E3E3E;
|
||||
th.background.color = 0xFF2B2B2B;
|
||||
th.text.color = { 0xFFFFFFFF, 0xFFFFFFFF, 0xFF6D6D6D, 0xFF6D6D6D };
|
||||
th.back.color = { 0xFF2B2B2B, Color::Swap(0xFF0078D4), 0xFF2B2B2B, 0xFF353535 };
|
||||
|
||||
th.border.padding.left = 4;
|
||||
th.border.padding.right = 4;
|
||||
th.border.radius = th.radius(2);
|
||||
th.back.radius = th.radius(1);
|
||||
th.back.padding.top = 0;
|
||||
th.back.padding.bottom = 0;
|
||||
th.back.margin = { 0, 4, 0, 4 };
|
||||
th.shadow.size = 3;
|
||||
|
||||
if(enableTransparency)
|
||||
{
|
||||
th.border.size = 1;
|
||||
th.border.color = th.background.color;
|
||||
th.border.color.a = 0x40;
|
||||
th.background.color.a = 0x00;
|
||||
th.background.tintcolor = th.background.color;
|
||||
th.background.tintcolor.a = 0x40;
|
||||
th.back.color.nor = 0x00000000;
|
||||
th.back.color.nor_dis = 0x00000000;
|
||||
th.back.color.sel.a = 0xaa;
|
||||
th.back.color.sel_dis.a = 0x80;
|
||||
th.separator.color = 0x15FFFFFF;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
th.separator.color = 0xFF808080;
|
||||
th.border.color = 0xFFA0A0A0;
|
||||
th.background.color = 0xFF2B2B2B;
|
||||
th.text.color = { 0xFFFFFFFF, 0xFFFFFFFF, 0xFF6D6D6D, 0xFF6D6D6D };
|
||||
th.back.color = { 0xFF2B2B2B, 0xFF414141, 0xFF2B2B2B, 0xFF2B2B2B };
|
||||
|
||||
if(enableTransparency)
|
||||
{
|
||||
th.border.size = 1;
|
||||
th.border.color = th.background.color;
|
||||
th.border.color.a = 0x40;
|
||||
th.background.color.a = 0x00;
|
||||
th.background.tintcolor = th.background.color;
|
||||
th.background.tintcolor.a = 0x40;
|
||||
th.back.color = { 0x00000000, 0x10FFFFFF, 0x00000000, 0x05FFFFFF };
|
||||
th.separator.color = 0x15FFFFFF;
|
||||
}
|
||||
}
|
||||
|
||||
th.shadow.color.opacity(25);
|
||||
//th.back.border = th.back.color.nor;
|
||||
th.set_symbols_as_text(1);
|
||||
|
||||
return th;
|
||||
}
|
||||
|
||||
static auto White(uint8_t enableTransparency = 0)
|
||||
{
|
||||
Theme th;
|
||||
if(Windows::Version::Instance().IsWindows11OrGreater())
|
||||
{
|
||||
th = Modern(ThemeType::White, 0);
|
||||
th.background.color = 0xFFFFFFFF;
|
||||
th.text.color = { 0xFF000000, 0xFF000000, 0xFF808080, 0xFF808080 };
|
||||
th.back.color = { 0xFFFFFFFF, 0xFFF0F0F0, 0xFFFFFFFF, 0xFFFFFFFF };
|
||||
}
|
||||
else
|
||||
{
|
||||
th = Default(ThemeType::White, 0);
|
||||
th.border.color = 0xFFE3E3E3;
|
||||
th.background.color = 0xFFFFFFFF;
|
||||
th.text.color = { 0xFF000000, 0xFF000000, 0xFF808080, 0xFF808080 };
|
||||
th.back.color = { 0xFFFFFFFF, 0xFFF0F0F0, 0xFFFFFFFF, 0xFFFFFFFF };
|
||||
}
|
||||
|
||||
if(enableTransparency)
|
||||
{
|
||||
th.border.size = 1;
|
||||
th.border.color = th.background.color;
|
||||
th.border.color.a = 0x40;
|
||||
th.background.color.a = 0x00;
|
||||
th.background.tintcolor = th.background.color;
|
||||
th.background.tintcolor.a = 0xff;
|
||||
th.back.color.nor = 0x00000000;
|
||||
th.back.color.nor_dis = 0x00000000;
|
||||
th.back.color.sel.a = 0xaa;
|
||||
th.back.color.sel_dis.a = 0x80;
|
||||
th.separator.color.a = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
th.separator.color = th.background.color;
|
||||
}
|
||||
|
||||
th.shadow.color.a = 0x10;
|
||||
//th.back.border = th.back.color.nor;
|
||||
|
||||
th.separator.size = 3;
|
||||
th.set_symbols_as_text(0);
|
||||
return th;
|
||||
}
|
||||
|
||||
static auto Black(uint8_t enableTransparency = 0)
|
||||
{
|
||||
Theme th;
|
||||
if(Windows::Version::Instance().IsWindows11OrGreater())
|
||||
{
|
||||
th = Modern(ThemeType::Black, 1);
|
||||
th.background.color = 0xFF000000;
|
||||
th.border.color = th.background.color;
|
||||
th.border.color = 0xFFFFFFFF;
|
||||
th.border.color.opacity(5);
|
||||
th.text.color = { 0xFFFFFFFF, 0xFFFFFFFF, 0xFF808080, 0xFF808080 };
|
||||
th.back.color = { 0xFF000000, 0xFF202020, 0xFF000000, 0xFF000000 };
|
||||
}
|
||||
else
|
||||
{
|
||||
th = Default(ThemeType::Black, 1);
|
||||
th.border.color = 0xFF111111;
|
||||
th.background.color = 0xFF000000;
|
||||
th.separator.margin = { 8, 3, 8, 3 };
|
||||
th.text.color = { 0xFFFFFFFF, 0xFFFFFFFF, 0xFF808080, 0xFF808080 };
|
||||
th.back.color = { 0xFF000000, 0xFF202020, 0xFF000000, 0xFF000000 };
|
||||
}
|
||||
|
||||
if(enableTransparency)
|
||||
{
|
||||
th.border.size = 1;
|
||||
th.border.color = th.background.color;
|
||||
th.border.color.a = 0x40;
|
||||
th.background.color.a = 0x00;
|
||||
th.background.tintcolor = th.background.color;
|
||||
th.background.tintcolor.a = 0xff;
|
||||
th.back.color.nor = 0x00000000;
|
||||
th.back.color.nor_dis = 0x00000000;
|
||||
th.back.color.sel= 0x10FFFFFF;
|
||||
th.back.color.sel_dis = 0x05FFFFFF;
|
||||
th.separator.color.a = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
th.separator.color = th.background.color;
|
||||
}
|
||||
|
||||
th.shadow.color.opacity(25);
|
||||
//th.back.border = th.back.color.nor;
|
||||
th.separator.size = 3;
|
||||
th.set_symbols_as_text(1);
|
||||
return th;
|
||||
}
|
||||
|
||||
template<typename T = long>
|
||||
static T DPI(double value, double dpi = 96)
|
||||
{
|
||||
return static_cast<T>(std::rint((value * dpi / 96.0)));
|
||||
}
|
||||
|
||||
static bool IsHighContrast()
|
||||
{
|
||||
HIGHCONTRASTW hc = { sizeof(HIGHCONTRASTW) };
|
||||
if(SystemParameters(SPI_GETHIGHCONTRAST, 0, &hc, 0))
|
||||
return hc.dwFlags & HCF_HIGHCONTRASTON;
|
||||
return false;
|
||||
}
|
||||
|
||||
static long GetFont(LOGFONTW *lf, uint32_t dpi = 96)
|
||||
{
|
||||
NONCLIENTMETRICSW ncm{};
|
||||
ncm.cbSize = sizeof(ncm);
|
||||
if(SystemParameters(SPI_GETNONCLIENTMETRICS, sizeof(ncm), &ncm, 0, dpi))
|
||||
{
|
||||
::memcpy(lf, &ncm.lfMenuFont, sizeof(LOGFONTW));
|
||||
return ncm.lfMenuFont.lfHeight;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
/*
|
||||
0 light
|
||||
1 dark
|
||||
2 system_dark
|
||||
3 apps_dark
|
||||
*/
|
||||
|
||||
//EnableTransparency
|
||||
static constexpr auto key_personalize = LR"(SOFTWARE\Microsoft\Windows\CurrentVersion\Themes\Personalize)";
|
||||
|
||||
static bool IsDarkMode(bool taskbar)
|
||||
{
|
||||
//Windows 10 build 10074
|
||||
static constexpr auto systemUsesLightTheme = L"SystemUsesLightTheme";
|
||||
//Windows 10 build 1809
|
||||
constexpr auto appsUseLightTheme = L"AppsUseLightTheme";
|
||||
|
||||
bool _systemUsesLightTheme = true;
|
||||
bool _appsUseLightTheme = true;
|
||||
|
||||
if(!IsHighContrast())
|
||||
{
|
||||
auto personalize = Registry::CurrentUser.OpenSubKey(key_personalize, false, false);
|
||||
if(personalize)
|
||||
{
|
||||
//Windows 10 build 10074
|
||||
if(personalize.ExistsValue(systemUsesLightTheme))
|
||||
{
|
||||
_systemUsesLightTheme = static_cast<bool>(personalize.GetDWord(systemUsesLightTheme));
|
||||
//Windows 10 build 1809
|
||||
if(personalize.ExistsValue(appsUseLightTheme))
|
||||
_appsUseLightTheme = static_cast<bool>(personalize.GetDWord(appsUseLightTheme));
|
||||
}
|
||||
personalize.Close();
|
||||
}
|
||||
}
|
||||
return taskbar ? !_systemUsesLightTheme : !_appsUseLightTheme;
|
||||
}
|
||||
|
||||
static void Personalize(bool *lpSystemUsesLightTheme = nullptr, bool *lpAppsUseLightTheme = nullptr, bool *lpEnableTransparency = nullptr)
|
||||
{
|
||||
static constexpr auto enableTransparency = L"EnableTransparency";
|
||||
//Windows 10 build 10074
|
||||
static constexpr auto systemUsesLightTheme = L"SystemUsesLightTheme";
|
||||
//Windows 10 build 1809
|
||||
constexpr auto appsUseLightTheme = L"AppsUseLightTheme";
|
||||
|
||||
if(!IsHighContrast())
|
||||
{
|
||||
auto personalize = Registry::CurrentUser.OpenSubKey(key_personalize, false, false);
|
||||
if(personalize)
|
||||
{
|
||||
if(lpEnableTransparency)
|
||||
{
|
||||
*lpEnableTransparency = false;
|
||||
if(personalize.ExistsValue(enableTransparency))
|
||||
{
|
||||
*lpEnableTransparency = static_cast<bool>(personalize.GetDWord(enableTransparency));
|
||||
}
|
||||
}
|
||||
|
||||
//Windows 10 build 10074
|
||||
if(lpSystemUsesLightTheme)
|
||||
{
|
||||
*lpSystemUsesLightTheme = true;
|
||||
if(personalize.ExistsValue(systemUsesLightTheme))
|
||||
*lpSystemUsesLightTheme = static_cast<bool>(personalize.GetDWord(systemUsesLightTheme));
|
||||
}
|
||||
|
||||
//Windows 10 build 1809
|
||||
if(lpAppsUseLightTheme)
|
||||
{
|
||||
*lpAppsUseLightTheme = true;
|
||||
if(personalize.ExistsValue(appsUseLightTheme))
|
||||
*lpAppsUseLightTheme = static_cast<bool>(personalize.GetDWord(appsUseLightTheme));
|
||||
}
|
||||
personalize.Close();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
static bool SystemParameters(uint32_t uiAction, uint32_t uiParam, void* pvParam, uint32_t fWinIni, uint32_t dpi = 96, bool skip_dpi = false)
|
||||
{
|
||||
if(!skip_dpi and ver.IsWindowsVersionOrGreater(10, 0, 14393))
|
||||
return DLL::User32<BOOL>("SystemParametersInfoForDpi", uiAction, uiParam, pvParam, fWinIni, dpi);
|
||||
return ::SystemParametersInfoW(uiAction, uiParam, pvParam, fWinIni);
|
||||
}
|
||||
|
||||
template<typename T = int>
|
||||
static T SystemMetrics(int nIndex, uint32_t dpi = 96, bool skip_dpi = false)
|
||||
{
|
||||
if(!skip_dpi and ver.IsWindowsVersionOrGreater(10, 0, 14393))
|
||||
return DLL::User32<T>("GetSystemMetricsForDpi", nIndex, dpi);
|
||||
return static_cast<T>(::GetSystemMetrics(nIndex));
|
||||
}
|
||||
|
||||
static uint32_t GetDpi(HWND hWnd)
|
||||
{
|
||||
if(ver.IsWindowsVersionOrGreater(10, 0, 14393))
|
||||
return DLL::User32<uint32_t>("GetDpiForWindow", hWnd);
|
||||
return (uint32_t)DC(hWnd).GetDeviceCapsX();
|
||||
}
|
||||
|
||||
static uint32_t GetDpi(Point const &pt, HWND hWnd = nullptr)
|
||||
{
|
||||
auto dpiX = 96u, dpiY = 96u;
|
||||
if(ver.IsWindows81OrGreater())
|
||||
{
|
||||
if(auto hMonitor = ::MonitorFromPoint(pt, MONITOR_DEFAULTTONEAREST); hMonitor)
|
||||
{
|
||||
if(S_OK == DLL::Invoke<HRESULT>(L"Shcore.dll", "GetDpiForMonitor", hMonitor, 0, &dpiX, &dpiY) && dpiX != 0)
|
||||
return dpiX;
|
||||
}
|
||||
}
|
||||
|
||||
if(hWnd)
|
||||
{
|
||||
if(ver.IsWindowsVersionOrGreater(10, 0, 14393))
|
||||
return DLL::User32<uint32_t>("GetDpiForWindow", hWnd);
|
||||
return (uint32_t)DC(hWnd).GetDeviceCapsY();
|
||||
}
|
||||
|
||||
return dpiX;
|
||||
}
|
||||
|
||||
static HTHEME OpenThemeData(HWND hWnd, wchar_t const *pszClassList, uint32_t dpi = 96)
|
||||
{
|
||||
if(ver.IsWindowsVersionOrGreater(10, 0, 14393))
|
||||
return DLL::Invoke<HTHEME>(L"uxtheme.dll", "OpenThemeDataForDpi", hWnd, pszClassList, dpi);
|
||||
return ::OpenThemeData(hWnd, pszClassList);
|
||||
}
|
||||
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,85 @@
|
||||
#pragma once
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
struct Tip
|
||||
{
|
||||
static constexpr auto IDT_SHOW = 0x100; //the identifier of the timer for show
|
||||
static constexpr auto IDT_HIDE = 0x101; //the identifier of the timer for hide
|
||||
|
||||
static constexpr auto TIMEIN = 1000;
|
||||
static constexpr auto TIMEOUT = 1000 * 60;
|
||||
static constexpr auto MAXWIDTH = 640;
|
||||
static constexpr auto MAXHEIGHT = 100;
|
||||
|
||||
HWND handle{};
|
||||
Rect rect;
|
||||
string text;
|
||||
uint8_t type = 0;
|
||||
uint16_t time = UINT16_MAX;
|
||||
|
||||
bool enabled = true;
|
||||
bool visible{};
|
||||
HFONT hfont{};
|
||||
class ContextMenu *ctx{};
|
||||
Expression *e{};
|
||||
|
||||
Tip()
|
||||
{
|
||||
}
|
||||
|
||||
~Tip()
|
||||
{
|
||||
destroy();
|
||||
}
|
||||
|
||||
bool create()
|
||||
{
|
||||
if(!handle)
|
||||
{
|
||||
handle = ::CreateWindowExW(WS_EX_TOPMOST | WS_EX_TRANSPARENT | WS_EX_LAYERED | WS_EX_NOACTIVATE, WC_Shell_Window,
|
||||
L"Tip", WS_POPUP,
|
||||
0, 0, 1, 1, nullptr, nullptr, nullptr, nullptr);
|
||||
if(handle)
|
||||
{
|
||||
::SetWindowSubclass(handle, [](HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam,
|
||||
UINT_PTR, DWORD_PTR dwRefData)->LRESULT
|
||||
{
|
||||
if(auto _this = reinterpret_cast<Tip *>(dwRefData); _this)
|
||||
return _this->Proc(hWnd, uMsg, wParam, lParam);
|
||||
return ::DefSubclassProc(hWnd, uMsg, wParam, lParam);
|
||||
}, 0, reinterpret_cast<DWORD_PTR>(this));
|
||||
}
|
||||
}
|
||||
return handle;
|
||||
}
|
||||
|
||||
bool show();
|
||||
bool show(Expression *e, const Rect &rc);
|
||||
bool show(const string &text, uint8_t type, uint16_t time, const Rect &rc);
|
||||
bool hide(bool cancel = false);
|
||||
LRESULT Proc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam);
|
||||
|
||||
void destroy()
|
||||
{
|
||||
killTimer();
|
||||
if(handle)
|
||||
::DestroyWindow(handle);
|
||||
handle = nullptr;
|
||||
visible = false;
|
||||
}
|
||||
|
||||
private:
|
||||
void killTimer()
|
||||
{
|
||||
if(handle)
|
||||
{
|
||||
::KillTimer(handle, IDT_SHOW);
|
||||
::KillTimer(handle, IDT_HIDE);
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,235 @@
|
||||
#pragma once
|
||||
#include "Include\Theme.h"
|
||||
|
||||
namespace Nilesoft
|
||||
{
|
||||
namespace Shell
|
||||
{
|
||||
/*
|
||||
//Windows 10 build 10586 (also known as the November Update or version 1511)
|
||||
//Windows 10 >= (v1507, b10240), (v1511, b10586) Taskbar contextmenu darkmode
|
||||
|
||||
ctober 2018 Update (version 1809)
|
||||
HKEY_CURRENT_USER\SOFTWARE\Microsoft\Windows\CurrentVersion\Themes\Personalize
|
||||
AppsUseLightTheme==1 && SystemUsesLightTheme==1; > explorer_menu_light | taskbar_menu_light
|
||||
AppsUseLightTheme==0 && SystemUsesLightTheme==0; > explorer_menu_dark | taskbar_menu_dark
|
||||
|
||||
AppsUseLightTheme==0 && SystemUsesLightTheme==1; > explorer_menu_dark | taskbar_menu_light
|
||||
AppsUseLightTheme==1 && SystemUsesLightTheme==0; > explorer_menu_light | taskbar_menu_dark
|
||||
|
||||
//windows 10 build 10162 1607
|
||||
|
||||
//Windows 10 build 10586 (also known as the November Update or version 1511)
|
||||
//Windows 10 >= (v1507, b10240), (v1511, b10586) Taskbar contextmenu darkmode
|
||||
//
|
||||
//Windows 10 build 10586 (also known as the November Update or version 1511)
|
||||
//Windows 10 >= (v1507, b10240), (v1511, b10586) Taskbar contextmenu darkmode
|
||||
*/
|
||||
class UxTheme : public Theme
|
||||
{
|
||||
Version* m_version = nullptr;
|
||||
HTHEME _handle;
|
||||
|
||||
public:
|
||||
int transparent = 0;
|
||||
SIZE image_size{};
|
||||
|
||||
public:
|
||||
|
||||
UxTheme(HTHEME handle =nullptr)
|
||||
: _handle{ handle }, m_version{ &Version::Instance() }
|
||||
{
|
||||
}
|
||||
|
||||
~UxTheme() { close(); }
|
||||
|
||||
operator HTHEME() const { return _handle; }
|
||||
explicit operator bool() const { return _handle != nullptr; }
|
||||
|
||||
bool open(HWND hWnd, const wchar_t *classList)
|
||||
{
|
||||
close();
|
||||
_handle = ::OpenThemeData(hWnd, classList);
|
||||
return _handle != nullptr;
|
||||
}
|
||||
|
||||
void close()
|
||||
{
|
||||
if(_handle)
|
||||
::CloseThemeData(_handle);
|
||||
_handle = nullptr;
|
||||
}
|
||||
|
||||
bool get_text_color(int partId, int stateId, COLORREF &color)
|
||||
{
|
||||
if(_handle)
|
||||
{
|
||||
if(S_OK == ::GetThemeColor(_handle, partId, stateId, TMT_TEXTCOLOR, &color))
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool get_background_color(int partId, int stateId, COLORREF &color)
|
||||
{
|
||||
if(_handle)
|
||||
{
|
||||
if(S_OK == ::GetThemeColor(_handle, partId, stateId, TMT_FILLCOLOR, &color))
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
HBITMAP get_bitmap(int partId, int stateId)
|
||||
{
|
||||
if(_handle)
|
||||
{
|
||||
HBITMAP result = nullptr;
|
||||
if(S_OK == ::GetThemeBitmap(_handle, partId, stateId, TMT_DIBDATA, GBF_DIRECT, &result))
|
||||
{
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
bool draw_text(HDC hdc, int partId, int stateId, const wchar_t *text, int cchText, uint32_t dwTextFlags, uint32_t dwTextFlags2, const RECT *pRect) const
|
||||
{
|
||||
return S_OK == ::DrawThemeText(_handle, hdc, partId, stateId, text, cchText, dwTextFlags, dwTextFlags2, pRect);
|
||||
}
|
||||
|
||||
bool draw_background(HDC hdc, int partId, int stateId, const RECT *pRect, const RECT *pClipRect = nullptr) const
|
||||
{
|
||||
return S_OK == ::DrawThemeBackground(_handle, hdc, partId, stateId, pRect, pClipRect);
|
||||
}
|
||||
|
||||
/*bool draw_background(HDC hdc, int partId, int stateId, const RECT *pRect, const RECT *pClipRect = nullptr) const
|
||||
{
|
||||
return S_OK == ::DrawThemeIcon(_handle, hdc, partId, stateId, pRect, pClipRect);
|
||||
}*/
|
||||
|
||||
bool is_part_defined(int partId, int stateId) const
|
||||
{
|
||||
return IsThemePartDefined(_handle, partId, stateId);
|
||||
}
|
||||
|
||||
bool get_text_extent(HDC hdc, int partId, int stateId, const wchar_t *text, int cch, uint32_t dwTextFlags, const RECT *pBoundingRect, RECT *pExtentRect) const
|
||||
{
|
||||
return S_OK == ::GetThemeTextExtent(_handle, hdc, partId, stateId, text, cch, dwTextFlags, pBoundingRect, pExtentRect);
|
||||
}
|
||||
|
||||
static std::tuple<COLORREF, COLORREF> GetColor(bool dark, HWND hWnd = nullptr)
|
||||
{
|
||||
COLORREF clr_menu = dark ? 0x000000 : 0xFFFFFF;
|
||||
COLORREF clr_menu_text = dark ? 0xFFFFFF : 0x000000;
|
||||
|
||||
if(IsHighContrast())
|
||||
{
|
||||
clr_menu_text = ::GetSysColor(COLOR_MENUTEXT);
|
||||
clr_menu = ::GetSysColor(COLOR_MENU);
|
||||
}
|
||||
else
|
||||
{
|
||||
if(hWnd == nullptr)
|
||||
hWnd = ::GetDesktopWindow();
|
||||
|
||||
UxTheme theme;
|
||||
|
||||
//IsThemePartDefined
|
||||
if(dark)
|
||||
{
|
||||
if(!theme.open(hWnd, L"ImmersiveStartDark::Menu"))
|
||||
{
|
||||
if(!theme.open(hWnd, L"DarkMode_ImmersiveStart::Menu"))
|
||||
{
|
||||
if(!theme.open(hWnd, L"DarkMode::Menu"))
|
||||
{
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if(!theme.open(hWnd, L"ImmersiveStart::Menu"))
|
||||
{
|
||||
theme.open(hWnd, VSCLASS_MENU);
|
||||
}
|
||||
}
|
||||
|
||||
if(theme)
|
||||
{
|
||||
theme.get_text_color(MENU_POPUPITEM, MPI_NORMAL, clr_menu_text);
|
||||
|
||||
if(!theme.get_background_color(MENU_POPUPBACKGROUND, MPI_NORMAL, clr_menu))
|
||||
{
|
||||
auto bmp = theme.get_bitmap(MENU_POPUPITEM, MPI_NORMAL);
|
||||
if(bmp)
|
||||
{
|
||||
if(auto dc = ::CreateCompatibleDC(nullptr))
|
||||
{
|
||||
auto old = ::SelectObject(dc, bmp);
|
||||
clr_menu = ::GetPixel(dc, 0, 0);
|
||||
::SelectObject(dc, old);
|
||||
::DeleteDC(dc);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
return std::make_tuple(clr_menu_text, clr_menu);
|
||||
}
|
||||
|
||||
/*
|
||||
HRESULT CMenuMetrics::Initialize()
|
||||
{
|
||||
HRESULT hr = E_FAIL;
|
||||
hTheme = OpenThemeData(hwndTheme, VSCLASS_MENU);
|
||||
if (hTheme)
|
||||
{
|
||||
GetThemePartSize(hTheme, NULL, MENU_POPUPCHECK, 0, NULL, TS_TRUE, &sizePopupCheck);
|
||||
GetThemeInt(hTheme, MENU_POPUPITEM, 0, TMT_BORDERSIZE, &iPopupBorderSize);
|
||||
GetThemeMargins(hTheme, NULL, MENU_POPUPCHECK, 0, TMT_CONTENTMARGINS, NULL, &marPopupCheck);
|
||||
hr = S_OK;
|
||||
}
|
||||
return hr;
|
||||
}
|
||||
|
||||
An HTHEME is requested from the parent window which maps to the menu class.
|
||||
If it succeeds we then ask for the metrics we will need to properly measure and layout our menu items.
|
||||
Modifying Owner-Draw code – Measurement
|
||||
|
||||
There are several “Get” functions that return information on a part/state:
|
||||
|
||||
GetThemePartSize() will give you the dimensions of a part/state pair.
|
||||
GetThemeMargins() will give you the spacing around a part/state pair.
|
||||
GetThemeInt(…, TMT_BORDERSIZE, …) will give you the size of the border around a part/state pair
|
||||
GetThemeTextExtent() will give you the dimensions of the text you specify using the correct font for the part/state pair.
|
||||
The parameters are similar to the DrawText API, including a parameter that accepts DT_* flags.
|
||||
|
||||
This information will enable you to make the appropriate measurement and layout calculations.
|
||||
In the test app CMenuMetrics caches these metrics and provides some helper functions, like ToMeasureSize() which applies the specified margins to the tight bounding box you calculated for the menu item.
|
||||
Modifying Owner-Draw code – Drawing
|
||||
The first thing you need to do is convert the DRAWITEMSTRUCT’s itemState field into the correct state id (POPUPITEMSTATES for popup menus.)
|
||||
For example, ODS_HOTLIGHT gets translated to MPI_HOT and ODS_INACTIVE can get translated to MPI_DISABLED. See CMenuMetrics::ToItemStateId() for details.
|
||||
The next thing you do is layout the items according to the metrics you calculated during WM_MEASUREITEM and draw the menu in layers using DrawThemeBackground(), starting from the bottom layer:
|
||||
MENU_POPUPBACKGROUND (if the background contains transparency)
|
||||
MENU_POPUPGUTTER (if you want a gutter)
|
||||
MENU_POPUPSEPARATOR (if the item is a separator)
|
||||
MENU_POPUPITEM
|
||||
MENU_POPUPCHECKBACKPGROUND (if you are rendering a checkmark)
|
||||
MENU_POPUPCHECK (if you are rendering a checkmark)
|
||||
DrawThemeText(…, MENU_POPUPITEM, …)
|
||||
|
||||
CVistaOwnerDraw::_DrawMenuItem() demonstrates this process.
|
||||
|
||||
Special considerations
|
||||
Allowing the test app to switch between owner-draw and non-owner draw menus presented an interesting issue: USER does not issue new WM_MEASUREITEM messages when the MFT_OWNERDRAW bit is toggled so it continues to use the old metrics. This may be old news (it appears to have always worked this way) but it was a surprise to me.
|
||||
Fortunately there is a simple workaround: make sure fMask has MIIM_BITMAP set when you call SetMenuItemInfo() and this will cause new WM_MEASUREITEM messages to be sent. The ResetMenuMetrics() helper function will clear out all the menu items of the specified hmenu. A more efficient method would be to set this bit when flipping the MFT_OWNERDRAW bit but I wanted to call this out clearly in the sample code. The MakeOwnerDraw() helper function is used by the test app to change between owner-draw and non-owner-draw.
|
||||
Important details not covered in article
|
||||
The sample code presents a simplified version of menu rendering in order to explain the basic concepts. It does not use every part and state (no submenu rendering), it does not cover the menu bar, and it will not necessarily line up to the pixel with the system’s menu rendering. If you are in the business of custom rendered menus then I don’t believe any of these simplifications will be an issue for you.
|
||||
At this point someone may say “Why didn’t you make an API that would render portions of the menu to make all this easier?” The answer to that is a familiar one: time and resources. Vista was a big undertaking and we had plenty to do in order to get it wrapped up and out the door.
|
||||
*/
|
||||
};
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,465 @@
|
||||
#pragma once
|
||||
/*
|
||||
* stb_image_write.h
|
||||
*
|
||||
* Copyright (c) 2017 Sean Barrett
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a copy of
|
||||
* this software and associated documentation files (the "Software"), to deal in
|
||||
* the Software without restriction, including without limitation the rights to
|
||||
* use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
|
||||
* of the Software, and to permit persons to whom the Software is furnished to do
|
||||
* so, subject to the following conditions:
|
||||
* The above copyright notice and this permission notice shall be included in all
|
||||
* copies or substantial portions of the Software.
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
|
||||
#include <stdlib.h>
|
||||
#include <stdio.h>
|
||||
#include <string.h>
|
||||
#include <assert.h>
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////////
|
||||
//
|
||||
// PNG writer
|
||||
//
|
||||
|
||||
#ifndef STBIW_MALLOC
|
||||
#define STBIW_MALLOC(sz) malloc(sz)
|
||||
#define STBIW_REALLOC(p,newsz) realloc(p,newsz)
|
||||
#define STBIW_FREE(p) free(p)
|
||||
#endif
|
||||
|
||||
#ifndef STBIW_REALLOC_SIZED
|
||||
#define STBIW_REALLOC_SIZED(p,oldsz,newsz) STBIW_REALLOC(p,newsz)
|
||||
#endif
|
||||
|
||||
#ifndef STBIW_MEMMOVE
|
||||
#define STBIW_MEMMOVE(a,b,sz) memmove(a,b,sz)
|
||||
#endif
|
||||
|
||||
#ifndef STBIW_ASSERT
|
||||
#include <assert.h>
|
||||
#define STBIW_ASSERT(x) assert(x)
|
||||
#endif
|
||||
|
||||
#define STBIW_UCHAR(x) (unsigned char) ((x) & 0xff)
|
||||
|
||||
typedef unsigned int stbiw_uint32;
|
||||
|
||||
static int stbi__flip_vertically_on_write = 0;
|
||||
static int stbi_write_force_png_filter = -1;
|
||||
static int stbi_write_png_compression_level = 8;
|
||||
|
||||
#define stbiw__sbraw(a) ((int *) (void *) (a) - 2)
|
||||
#define stbiw__sbm(a) stbiw__sbraw(a)[0]
|
||||
#define stbiw__sbn(a) stbiw__sbraw(a)[1]
|
||||
|
||||
#define stbiw__sbneedgrow(a,n) ((a)==0 || stbiw__sbn(a)+n >= stbiw__sbm(a))
|
||||
#define stbiw__sbmaybegrow(a,n) (stbiw__sbneedgrow(a,(n)) ? stbiw__sbgrow(a,n) : 0)
|
||||
#define stbiw__sbgrow(a,n) stbiw__sbgrowf((void **) &(a), (n), sizeof(*(a)))
|
||||
|
||||
#define stbiw__sbpush(a, v) (stbiw__sbmaybegrow(a,1), (a)[stbiw__sbn(a)++] = (v))
|
||||
#define stbiw__sbcount(a) ((a) ? stbiw__sbn(a) : 0)
|
||||
#define stbiw__sbfree(a) ((a) ? STBIW_FREE(stbiw__sbraw(a)),0 : 0)
|
||||
|
||||
static void *stbiw__sbgrowf(void **arr, int increment, int itemsize)
|
||||
{
|
||||
int m = *arr ? 2 * stbiw__sbm(*arr) + increment : increment + 1;
|
||||
void *p = STBIW_REALLOC_SIZED(*arr ? stbiw__sbraw(*arr) : 0, *arr ? (stbiw__sbm(*arr) * itemsize + sizeof(int) * 2) : 0, itemsize * m + sizeof(int) * 2);
|
||||
STBIW_ASSERT(p);
|
||||
if(p) {
|
||||
if(!*arr) ((int *)p)[1] = 0;
|
||||
*arr = (void *)((int *)p + 2);
|
||||
stbiw__sbm(*arr) = m;
|
||||
}
|
||||
return *arr;
|
||||
}
|
||||
|
||||
static unsigned char *stbiw__zlib_flushf(unsigned char *data, unsigned int *bitbuffer, int *bitcount)
|
||||
{
|
||||
while(*bitcount >= 8) {
|
||||
stbiw__sbpush(data, STBIW_UCHAR(*bitbuffer));
|
||||
*bitbuffer >>= 8;
|
||||
*bitcount -= 8;
|
||||
}
|
||||
return data;
|
||||
}
|
||||
|
||||
static int stbiw__zlib_bitrev(int code, int codebits)
|
||||
{
|
||||
int res = 0;
|
||||
while(codebits--) {
|
||||
res = (res << 1) | (code & 1);
|
||||
code >>= 1;
|
||||
}
|
||||
return res;
|
||||
}
|
||||
|
||||
static unsigned int stbiw__zlib_countm(unsigned char *a, unsigned char *b, int limit)
|
||||
{
|
||||
int i;
|
||||
for(i = 0; i < limit && i < 258; ++i)
|
||||
if(a[i] != b[i]) break;
|
||||
return i;
|
||||
}
|
||||
|
||||
static unsigned int stbiw__zhash(unsigned char *data)
|
||||
{
|
||||
stbiw_uint32 hash = data[0] + (data[1] << 8) + (data[2] << 16);
|
||||
hash ^= hash << 3;
|
||||
hash += hash >> 5;
|
||||
hash ^= hash << 4;
|
||||
hash += hash >> 17;
|
||||
hash ^= hash << 25;
|
||||
hash += hash >> 6;
|
||||
return hash;
|
||||
}
|
||||
|
||||
#define stbiw__zlib_flush() (out = stbiw__zlib_flushf(out, &bitbuf, &bitcount))
|
||||
#define stbiw__zlib_add(code,codebits) \
|
||||
(bitbuf |= (code) << bitcount, bitcount += (codebits), stbiw__zlib_flush())
|
||||
#define stbiw__zlib_huffa(b,c) stbiw__zlib_add(stbiw__zlib_bitrev(b,c),c)
|
||||
// default huffman tables
|
||||
#define stbiw__zlib_huff1(n) stbiw__zlib_huffa(0x30 + (n), 8)
|
||||
#define stbiw__zlib_huff2(n) stbiw__zlib_huffa(0x190 + (n)-144, 9)
|
||||
#define stbiw__zlib_huff3(n) stbiw__zlib_huffa(0 + (n)-256,7)
|
||||
#define stbiw__zlib_huff4(n) stbiw__zlib_huffa(0xc0 + (n)-280,8)
|
||||
#define stbiw__zlib_huff(n) ((n) <= 143 ? stbiw__zlib_huff1(n) : (n) <= 255 ? stbiw__zlib_huff2(n) : (n) <= 279 ? stbiw__zlib_huff3(n) : stbiw__zlib_huff4(n))
|
||||
#define stbiw__zlib_huffb(n) ((n) <= 143 ? stbiw__zlib_huff1(n) : stbiw__zlib_huff2(n))
|
||||
|
||||
#define stbiw__ZHASH 16384
|
||||
|
||||
static unsigned char *stbi_zlib_compress(unsigned char *data, int data_len, int *out_len, int quality)
|
||||
{
|
||||
static unsigned short lengthc[] = { 3,4,5,6,7,8,9,10,11,13,15,17,19,23,27,31,35,43,51,59,67,83,99,115,131,163,195,227,258, 259 };
|
||||
static unsigned char lengtheb[] = { 0,0,0,0,0,0,0, 0, 1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3, 4, 4, 4, 4, 5, 5, 5, 5, 0 };
|
||||
static unsigned short distc[] = { 1,2,3,4,5,7,9,13,17,25,33,49,65,97,129,193,257,385,513,769,1025,1537,2049,3073,4097,6145,8193,12289,16385,24577, 32768 };
|
||||
static unsigned char disteb[] = { 0,0,0,0,1,1,2,2,3,3,4,4,5,5,6,6,7,7,8,8,9,9,10,10,11,11,12,12,13,13 };
|
||||
unsigned int bitbuf = 0;
|
||||
int i, j, bitcount = 0;
|
||||
unsigned char *out = NULL;
|
||||
unsigned char ***hash_table = (unsigned char ***)STBIW_MALLOC(stbiw__ZHASH * sizeof(unsigned char **));
|
||||
if(hash_table == NULL)
|
||||
return NULL;
|
||||
if(quality < 5) quality = 5;
|
||||
|
||||
stbiw__sbpush(out, 0x78); // DEFLATE 32K window
|
||||
stbiw__sbpush(out, 0x5e); // FLEVEL = 1
|
||||
stbiw__zlib_add(1, 1); // BFINAL = 1
|
||||
stbiw__zlib_add(1, 2); // BTYPE = 1 -- fixed huffman
|
||||
|
||||
for(i = 0; i < stbiw__ZHASH; ++i)
|
||||
hash_table[i] = NULL;
|
||||
|
||||
i = 0;
|
||||
while(i < data_len - 3) {
|
||||
// hash next 3 bytes of data to be compressed
|
||||
int h = stbiw__zhash(data + i) & (stbiw__ZHASH - 1), best = 3;
|
||||
unsigned char *bestloc = 0;
|
||||
unsigned char **hlist = hash_table[h];
|
||||
int n = stbiw__sbcount(hlist);
|
||||
for(j = 0; j < n; ++j) {
|
||||
if(hlist[j] - data > i - 32768) { // if entry lies within window
|
||||
int d = stbiw__zlib_countm(hlist[j], data + i, data_len - i);
|
||||
if(d >= best) { best = d; bestloc = hlist[j]; }
|
||||
}
|
||||
}
|
||||
// when hash table entry is too long, delete half the entries
|
||||
if(hash_table[h] && stbiw__sbn(hash_table[h]) == 2 * quality) {
|
||||
STBIW_MEMMOVE(hash_table[h], hash_table[h] + quality, sizeof(hash_table[h][0]) * quality);
|
||||
stbiw__sbn(hash_table[h]) = quality;
|
||||
}
|
||||
stbiw__sbpush(hash_table[h], data + i);
|
||||
|
||||
if(bestloc) {
|
||||
// "lazy matching" - check match at *next* byte, and if it's better, do cur byte as literal
|
||||
h = stbiw__zhash(data + i + 1) & (stbiw__ZHASH - 1);
|
||||
hlist = hash_table[h];
|
||||
n = stbiw__sbcount(hlist);
|
||||
for(j = 0; j < n; ++j) {
|
||||
if(hlist[j] - data > i - 32767) {
|
||||
int e = stbiw__zlib_countm(hlist[j], data + i + 1, data_len - i - 1);
|
||||
if(e > best) { // if next match is better, bail on current match
|
||||
bestloc = NULL;
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if(bestloc) {
|
||||
int d = (int)(data + i - bestloc); // distance back
|
||||
STBIW_ASSERT(d <= 32767 && best <= 258);
|
||||
for(j = 0; best > lengthc[j + 1] - 1; ++j);
|
||||
stbiw__zlib_huff(j + 257);
|
||||
if(lengtheb[j]) stbiw__zlib_add(best - lengthc[j], lengtheb[j]);
|
||||
for(j = 0; d > distc[j + 1] - 1; ++j);
|
||||
stbiw__zlib_add(stbiw__zlib_bitrev(j, 5), 5);
|
||||
if(disteb[j]) stbiw__zlib_add(d - distc[j], disteb[j]);
|
||||
i += best;
|
||||
}
|
||||
else {
|
||||
stbiw__zlib_huffb(data[i]);
|
||||
++i;
|
||||
}
|
||||
}
|
||||
// write out final bytes
|
||||
for(; i < data_len; ++i)
|
||||
stbiw__zlib_huffb(data[i]);
|
||||
stbiw__zlib_huff(256); // end of block
|
||||
// pad with 0 bits to byte boundary
|
||||
while(bitcount)
|
||||
stbiw__zlib_add(0, 1);
|
||||
|
||||
for(i = 0; i < stbiw__ZHASH; ++i)
|
||||
(void)stbiw__sbfree(hash_table[i]);
|
||||
STBIW_FREE(hash_table);
|
||||
|
||||
// store uncompressed instead if compression was worse
|
||||
if(stbiw__sbn(out) > data_len + 2 + ((data_len + 32766) / 32767) * 5) {
|
||||
stbiw__sbn(out) = 2; // truncate to DEFLATE 32K window and FLEVEL = 1
|
||||
for(j = 0; j < data_len;) {
|
||||
int blocklen = data_len - j;
|
||||
if(blocklen > 32767) blocklen = 32767;
|
||||
stbiw__sbpush(out, data_len - j == blocklen); // BFINAL = ?, BTYPE = 0 -- no compression
|
||||
stbiw__sbpush(out, STBIW_UCHAR(blocklen)); // LEN
|
||||
stbiw__sbpush(out, STBIW_UCHAR(blocklen >> 8));
|
||||
stbiw__sbpush(out, STBIW_UCHAR(~blocklen)); // NLEN
|
||||
stbiw__sbpush(out, STBIW_UCHAR(~blocklen >> 8));
|
||||
memcpy(out + stbiw__sbn(out), data + j, blocklen);
|
||||
stbiw__sbn(out) += blocklen;
|
||||
j += blocklen;
|
||||
}
|
||||
}
|
||||
|
||||
{
|
||||
// compute adler32 on input
|
||||
unsigned int s1 = 1, s2 = 0;
|
||||
int blocklen = (int)(data_len % 5552);
|
||||
j = 0;
|
||||
while(j < data_len) {
|
||||
for(i = 0; i < blocklen; ++i) { s1 += data[j + i]; s2 += s1; }
|
||||
s1 %= 65521; s2 %= 65521;
|
||||
j += blocklen;
|
||||
blocklen = 5552;
|
||||
}
|
||||
stbiw__sbpush(out, STBIW_UCHAR(s2 >> 8));
|
||||
stbiw__sbpush(out, STBIW_UCHAR(s2));
|
||||
stbiw__sbpush(out, STBIW_UCHAR(s1 >> 8));
|
||||
stbiw__sbpush(out, STBIW_UCHAR(s1));
|
||||
}
|
||||
*out_len = stbiw__sbn(out);
|
||||
// make returned pointer freeable
|
||||
STBIW_MEMMOVE(stbiw__sbraw(out), out, *out_len);
|
||||
return (unsigned char *)stbiw__sbraw(out);
|
||||
}
|
||||
|
||||
static unsigned int stbiw__crc32(unsigned char *buffer, int len)
|
||||
{
|
||||
static unsigned int crc_table[256] =
|
||||
{
|
||||
0x00000000, 0x77073096, 0xEE0E612C, 0x990951BA, 0x076DC419, 0x706AF48F, 0xE963A535, 0x9E6495A3,
|
||||
0x0eDB8832, 0x79DCB8A4, 0xE0D5E91E, 0x97D2D988, 0x09B64C2B, 0x7EB17CBD, 0xE7B82D07, 0x90BF1D91,
|
||||
0x1DB71064, 0x6AB020F2, 0xF3B97148, 0x84BE41DE, 0x1ADAD47D, 0x6DDDE4EB, 0xF4D4B551, 0x83D385C7,
|
||||
0x136C9856, 0x646BA8C0, 0xFD62F97A, 0x8A65C9EC, 0x14015C4F, 0x63066CD9, 0xFA0F3D63, 0x8D080DF5,
|
||||
0x3B6E20C8, 0x4C69105E, 0xD56041E4, 0xA2677172, 0x3C03E4D1, 0x4B04D447, 0xD20D85FD, 0xA50AB56B,
|
||||
0x35B5A8FA, 0x42B2986C, 0xDBBBC9D6, 0xACBCF940, 0x32D86CE3, 0x45DF5C75, 0xDCD60DCF, 0xABD13D59,
|
||||
0x26D930AC, 0x51DE003A, 0xC8D75180, 0xBFD06116, 0x21B4F4B5, 0x56B3C423, 0xCFBA9599, 0xB8BDA50F,
|
||||
0x2802B89E, 0x5F058808, 0xC60CD9B2, 0xB10BE924, 0x2F6F7C87, 0x58684C11, 0xC1611DAB, 0xB6662D3D,
|
||||
0x76DC4190, 0x01DB7106, 0x98D220BC, 0xEFD5102A, 0x71B18589, 0x06B6B51F, 0x9FBFE4A5, 0xE8B8D433,
|
||||
0x7807C9A2, 0x0F00F934, 0x9609A88E, 0xE10E9818, 0x7F6A0DBB, 0x086D3D2D, 0x91646C97, 0xE6635C01,
|
||||
0x6B6B51F4, 0x1C6C6162, 0x856530D8, 0xF262004E, 0x6C0695ED, 0x1B01A57B, 0x8208F4C1, 0xF50FC457,
|
||||
0x65B0D9C6, 0x12B7E950, 0x8BBEB8EA, 0xFCB9887C, 0x62DD1DDF, 0x15DA2D49, 0x8CD37CF3, 0xFBD44C65,
|
||||
0x4DB26158, 0x3AB551CE, 0xA3BC0074, 0xD4BB30E2, 0x4ADFA541, 0x3DD895D7, 0xA4D1C46D, 0xD3D6F4FB,
|
||||
0x4369E96A, 0x346ED9FC, 0xAD678846, 0xDA60B8D0, 0x44042D73, 0x33031DE5, 0xAA0A4C5F, 0xDD0D7CC9,
|
||||
0x5005713C, 0x270241AA, 0xBE0B1010, 0xC90C2086, 0x5768B525, 0x206F85B3, 0xB966D409, 0xCE61E49F,
|
||||
0x5EDEF90E, 0x29D9C998, 0xB0D09822, 0xC7D7A8B4, 0x59B33D17, 0x2EB40D81, 0xB7BD5C3B, 0xC0BA6CAD,
|
||||
0xEDB88320, 0x9ABFB3B6, 0x03B6E20C, 0x74B1D29A, 0xEAD54739, 0x9DD277AF, 0x04DB2615, 0x73DC1683,
|
||||
0xE3630B12, 0x94643B84, 0x0D6D6A3E, 0x7A6A5AA8, 0xE40ECF0B, 0x9309FF9D, 0x0A00AE27, 0x7D079EB1,
|
||||
0xF00F9344, 0x8708A3D2, 0x1E01F268, 0x6906C2FE, 0xF762575D, 0x806567CB, 0x196C3671, 0x6E6B06E7,
|
||||
0xFED41B76, 0x89D32BE0, 0x10DA7A5A, 0x67DD4ACC, 0xF9B9DF6F, 0x8EBEEFF9, 0x17B7BE43, 0x60B08ED5,
|
||||
0xD6D6A3E8, 0xA1D1937E, 0x38D8C2C4, 0x4FDFF252, 0xD1BB67F1, 0xA6BC5767, 0x3FB506DD, 0x48B2364B,
|
||||
0xD80D2BDA, 0xAF0A1B4C, 0x36034AF6, 0x41047A60, 0xDF60EFC3, 0xA867DF55, 0x316E8EEF, 0x4669BE79,
|
||||
0xCB61B38C, 0xBC66831A, 0x256FD2A0, 0x5268E236, 0xCC0C7795, 0xBB0B4703, 0x220216B9, 0x5505262F,
|
||||
0xC5BA3BBE, 0xB2BD0B28, 0x2BB45A92, 0x5CB36A04, 0xC2D7FFA7, 0xB5D0CF31, 0x2CD99E8B, 0x5BDEAE1D,
|
||||
0x9B64C2B0, 0xEC63F226, 0x756AA39C, 0x026D930A, 0x9C0906A9, 0xEB0E363F, 0x72076785, 0x05005713,
|
||||
0x95BF4A82, 0xE2B87A14, 0x7BB12BAE, 0x0CB61B38, 0x92D28E9B, 0xE5D5BE0D, 0x7CDCEFB7, 0x0BDBDF21,
|
||||
0x86D3D2D4, 0xF1D4E242, 0x68DDB3F8, 0x1FDA836E, 0x81BE16CD, 0xF6B9265B, 0x6FB077E1, 0x18B74777,
|
||||
0x88085AE6, 0xFF0F6A70, 0x66063BCA, 0x11010B5C, 0x8F659EFF, 0xF862AE69, 0x616BFFD3, 0x166CCF45,
|
||||
0xA00AE278, 0xD70DD2EE, 0x4E048354, 0x3903B3C2, 0xA7672661, 0xD06016F7, 0x4969474D, 0x3E6E77DB,
|
||||
0xAED16A4A, 0xD9D65ADC, 0x40DF0B66, 0x37D83BF0, 0xA9BCAE53, 0xDEBB9EC5, 0x47B2CF7F, 0x30B5FFE9,
|
||||
0xBDBDF21C, 0xCABAC28A, 0x53B39330, 0x24B4A3A6, 0xBAD03605, 0xCDD70693, 0x54DE5729, 0x23D967BF,
|
||||
0xB3667A2E, 0xC4614AB8, 0x5D681B02, 0x2A6F2B94, 0xB40BBE37, 0xC30C8EA1, 0x5A05DF1B, 0x2D02EF8D
|
||||
};
|
||||
|
||||
unsigned int crc = ~0u;
|
||||
int i;
|
||||
for(i = 0; i < len; ++i)
|
||||
crc = (crc >> 8) ^ crc_table[buffer[i] ^ (crc & 0xff)];
|
||||
return ~crc;
|
||||
}
|
||||
|
||||
#define stbiw__wpng4(o,a,b,c,d) ((o)[0]=STBIW_UCHAR(a),(o)[1]=STBIW_UCHAR(b),(o)[2]=STBIW_UCHAR(c),(o)[3]=STBIW_UCHAR(d),(o)+=4)
|
||||
#define stbiw__wp32(data,v) stbiw__wpng4(data, (v)>>24,(v)>>16,(v)>>8,(v));
|
||||
#define stbiw__wptag(data,s) stbiw__wpng4(data, s[0],s[1],s[2],s[3])
|
||||
|
||||
static void stbiw__wpcrc(unsigned char **data, int len)
|
||||
{
|
||||
unsigned int crc = stbiw__crc32(*data - len - 4, len + 4);
|
||||
stbiw__wp32(*data, crc);
|
||||
}
|
||||
|
||||
static unsigned char stbiw__paeth(int a, int b, int c)
|
||||
{
|
||||
int p = a + b - c, pa = abs(p - a), pb = abs(p - b), pc = abs(p - c);
|
||||
if(pa <= pb && pa <= pc) return STBIW_UCHAR(a);
|
||||
if(pb <= pc) return STBIW_UCHAR(b);
|
||||
return STBIW_UCHAR(c);
|
||||
}
|
||||
|
||||
// @OPTIMIZE: provide an option that always forces left-predict or paeth predict
|
||||
static void stbiw__encode_png_line(unsigned char *pixels, int stride_bytes, int width, int height, int y, int n, int filter_type, signed char *line_buffer)
|
||||
{
|
||||
static int mapping[] = { 0,1,2,3,4 };
|
||||
static int firstmap[] = { 0,1,0,5,6 };
|
||||
int *mymap = (y != 0) ? mapping : firstmap;
|
||||
int i;
|
||||
int type = mymap[filter_type];
|
||||
unsigned char *z = pixels + stride_bytes * (stbi__flip_vertically_on_write ? height - 1 - y : y);
|
||||
int signed_stride = stbi__flip_vertically_on_write ? -stride_bytes : stride_bytes;
|
||||
|
||||
if(type == 0) {
|
||||
memcpy(line_buffer, z, width * n);
|
||||
return;
|
||||
}
|
||||
|
||||
// first loop isn't optimized since it's just one pixel
|
||||
for(i = 0; i < n; ++i) {
|
||||
switch(type) {
|
||||
case 1: line_buffer[i] = z[i]; break;
|
||||
case 2: line_buffer[i] = z[i] - z[i - signed_stride]; break;
|
||||
case 3: line_buffer[i] = z[i] - (z[i - signed_stride] >> 1); break;
|
||||
case 4: line_buffer[i] = (signed char)(z[i] - stbiw__paeth(0, z[i - signed_stride], 0)); break;
|
||||
case 5: line_buffer[i] = z[i]; break;
|
||||
case 6: line_buffer[i] = z[i]; break;
|
||||
}
|
||||
}
|
||||
switch(type) {
|
||||
case 1: for(i = n; i < width * n; ++i) line_buffer[i] = z[i] - z[i - n]; break;
|
||||
case 2: for(i = n; i < width * n; ++i) line_buffer[i] = z[i] - z[i - signed_stride]; break;
|
||||
case 3: for(i = n; i < width * n; ++i) line_buffer[i] = z[i] - ((z[i - n] + z[i - signed_stride]) >> 1); break;
|
||||
case 4: for(i = n; i < width * n; ++i) line_buffer[i] = z[i] - stbiw__paeth(z[i - n], z[i - signed_stride], z[i - signed_stride - n]); break;
|
||||
case 5: for(i = n; i < width * n; ++i) line_buffer[i] = z[i] - (z[i - n] >> 1); break;
|
||||
case 6: for(i = n; i < width * n; ++i) line_buffer[i] = z[i] - stbiw__paeth(z[i - n], 0, 0); break;
|
||||
}
|
||||
}
|
||||
|
||||
static unsigned char *stbi_write_png_to_mem(const unsigned char *pixels, int stride_bytes, int x, int y, int n, int *out_len)
|
||||
{
|
||||
int force_filter = stbi_write_force_png_filter;
|
||||
int ctype[5] = { -1, 0, 4, 2, 6 };
|
||||
unsigned char sig[8] = { 137,80,78,71,13,10,26,10 };
|
||||
unsigned char *out, *o, *filt, *zlib;
|
||||
signed char *line_buffer;
|
||||
int j, zlen;
|
||||
|
||||
if(stride_bytes == 0)
|
||||
stride_bytes = x * n;
|
||||
|
||||
if(force_filter >= 5) {
|
||||
force_filter = -1;
|
||||
}
|
||||
|
||||
filt = (unsigned char *)STBIW_MALLOC((x * n + 1) * y); if(!filt) return 0;
|
||||
line_buffer = (signed char *)STBIW_MALLOC(x * n); if(!line_buffer) { STBIW_FREE(filt); return 0; }
|
||||
for(j = 0; j < y; ++j) {
|
||||
int filter_type;
|
||||
if(force_filter > -1) {
|
||||
filter_type = force_filter;
|
||||
stbiw__encode_png_line((unsigned char *)(pixels), stride_bytes, x, y, j, n, force_filter, line_buffer);
|
||||
}
|
||||
else { // Estimate the best filter by running through all of them:
|
||||
int best_filter = 0, best_filter_val = 0x7fffffff, est, i;
|
||||
for(filter_type = 0; filter_type < 5; filter_type++) {
|
||||
stbiw__encode_png_line((unsigned char *)(pixels), stride_bytes, x, y, j, n, filter_type, line_buffer);
|
||||
|
||||
// Estimate the entropy of the line using this filter; the less, the better.
|
||||
est = 0;
|
||||
for(i = 0; i < x * n; ++i) {
|
||||
est += abs((signed char)line_buffer[i]);
|
||||
}
|
||||
if(est < best_filter_val) {
|
||||
best_filter_val = est;
|
||||
best_filter = filter_type;
|
||||
}
|
||||
}
|
||||
if(filter_type != best_filter) { // If the last iteration already got us the best filter, don't redo it
|
||||
stbiw__encode_png_line((unsigned char *)(pixels), stride_bytes, x, y, j, n, best_filter, line_buffer);
|
||||
filter_type = best_filter;
|
||||
}
|
||||
}
|
||||
// when we get here, filter_type contains the filter type, and line_buffer contains the data
|
||||
filt[j * (x * n + 1)] = (unsigned char)filter_type;
|
||||
STBIW_MEMMOVE(filt + j * (x * n + 1) + 1, line_buffer, x * n);
|
||||
}
|
||||
STBIW_FREE(line_buffer);
|
||||
zlib = stbi_zlib_compress(filt, y * (x * n + 1), &zlen, stbi_write_png_compression_level);
|
||||
STBIW_FREE(filt);
|
||||
if(!zlib) return 0;
|
||||
|
||||
// each tag requires 12 bytes of overhead
|
||||
out = (unsigned char *)STBIW_MALLOC(8 + 12 + 13 + 12 + zlen + 12);
|
||||
if(!out) return 0;
|
||||
*out_len = 8 + 12 + 13 + 12 + zlen + 12;
|
||||
|
||||
o = out;
|
||||
STBIW_MEMMOVE(o, sig, 8); o += 8;
|
||||
stbiw__wp32(o, 13); // header length
|
||||
stbiw__wptag(o, "IHDR");
|
||||
stbiw__wp32(o, x);
|
||||
stbiw__wp32(o, y);
|
||||
*o++ = 8;
|
||||
*o++ = STBIW_UCHAR(ctype[n]);
|
||||
*o++ = 0;
|
||||
*o++ = 0;
|
||||
*o++ = 0;
|
||||
stbiw__wpcrc(&o, 13);
|
||||
|
||||
stbiw__wp32(o, zlen);
|
||||
stbiw__wptag(o, "IDAT");
|
||||
STBIW_MEMMOVE(o, zlib, zlen);
|
||||
o += zlen;
|
||||
STBIW_FREE(zlib);
|
||||
stbiw__wpcrc(&o, zlen);
|
||||
|
||||
stbiw__wp32(o, 0);
|
||||
stbiw__wptag(o, "IEND");
|
||||
stbiw__wpcrc(&o, 0);
|
||||
|
||||
STBIW_ASSERT(o == out + *out_len);
|
||||
|
||||
return out;
|
||||
}
|
||||
|
||||
int plutovg_stbi_write_png(const wchar_t *filename, int w, int h, const void *data)
|
||||
{
|
||||
FILE *f{};
|
||||
int len;
|
||||
auto png = stbi_write_png_to_mem((const unsigned char *)data, 0, w, h, 4, &len);
|
||||
|
||||
if(png == NULL) return 0;
|
||||
|
||||
_wfopen_s(&f, filename, L"wb");
|
||||
if(!f) { STBIW_FREE(png); return 0; }
|
||||
fwrite(png, 1, len, f);
|
||||
fclose(f);
|
||||
STBIW_FREE(png);
|
||||
return 1;
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
#pragma once
|
||||
|
||||
// Including SDKDDKVer.h defines the highest available Windows platform.
|
||||
|
||||
// If you wish to build your application for a previous Windows platform, include WinSDKVer.h and
|
||||
// set the _WIN32_WINNT macro to the platform you wish to support before including SDKDDKVer.h.
|
||||
|
||||
#include <SDKDDKVer.h>
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user