Introduce CSSLayoutSetLogger to pass the print result to C# side

Summary:
- CSSLayoutSetLogger
  - Problem: Unity or other logging system can't use printf output
  - Solution: Add CSSLogger to pass CSSNodePrint result to UnityEngine.Debug.Log or other logging system via CSSLogger function for debugging purpose

Reviewed By: emilsjolander

Differential Revision: D4027044

fbshipit-source-id: 90e2e449260888770f71fa7ea790ca9764d91c44
This commit is contained in:
Kazuki Sakamoto
2016-10-19 11:01:24 -07:00
committed by Facebook Github Bot
parent e4ad7d3c12
commit daed6f5b8a
11 changed files with 347 additions and 229 deletions

View File

@@ -98,6 +98,8 @@ typedef struct CSSNode {
static void _CSSNodeMarkDirty(const CSSNodeRef node); static void _CSSNodeMarkDirty(const CSSNodeRef node);
static CSSLogger gLogger = &printf;
static float static float
computedEdgeValue(const float edges[CSSEdgeCount], const CSSEdge edge, const float defaultValue) { computedEdgeValue(const float edges[CSSEdgeCount], const CSSEdge edge, const float defaultValue) {
CSS_ASSERT(edge <= CSSEdgeEnd, "Cannot get computed value of multi-edge shorthands"); CSS_ASSERT(edge <= CSSEdgeEnd, "Cannot get computed value of multi-edge shorthands");
@@ -375,19 +377,19 @@ static bool eq(const float a, const float b) {
static void indent(const uint32_t n) { static void indent(const uint32_t n) {
for (uint32_t i = 0; i < n; i++) { for (uint32_t i = 0; i < n; i++) {
printf(" "); gLogger(" ");
} }
} }
static void printNumberIfNotZero(const char *str, const float number) { static void printNumberIfNotZero(const char *str, const float number) {
if (!eq(number, 0)) { if (!eq(number, 0)) {
printf("%s: %g, ", str, number); gLogger("%s: %g, ", str, number);
} }
} }
static void printNumberIfNotUndefined(const char *str, const float number) { static void printNumberIfNotUndefined(const char *str, const float number) {
if (!CSSValueIsUndefined(number)) { if (!CSSValueIsUndefined(number)) {
printf("%s: %g, ", str, number); gLogger("%s: %g, ", str, number);
} }
} }
@@ -398,66 +400,66 @@ static bool eqFour(const float four[4]) {
static void static void
_CSSNodePrint(const CSSNodeRef node, const CSSPrintOptions options, const uint32_t level) { _CSSNodePrint(const CSSNodeRef node, const CSSPrintOptions options, const uint32_t level) {
indent(level); indent(level);
printf("{"); gLogger("{");
if (node->print) { if (node->print) {
node->print(node->context); node->print(node->context);
} }
if (options & CSSPrintOptionsLayout) { if (options & CSSPrintOptionsLayout) {
printf("layout: {"); gLogger("layout: {");
printf("width: %g, ", node->layout.dimensions[CSSDimensionWidth]); gLogger("width: %g, ", node->layout.dimensions[CSSDimensionWidth]);
printf("height: %g, ", node->layout.dimensions[CSSDimensionHeight]); gLogger("height: %g, ", node->layout.dimensions[CSSDimensionHeight]);
printf("top: %g, ", node->layout.position[CSSEdgeTop]); gLogger("top: %g, ", node->layout.position[CSSEdgeTop]);
printf("left: %g", node->layout.position[CSSEdgeLeft]); gLogger("left: %g", node->layout.position[CSSEdgeLeft]);
printf("}, "); gLogger("}, ");
} }
if (options & CSSPrintOptionsStyle) { if (options & CSSPrintOptionsStyle) {
if (node->style.flexDirection == CSSFlexDirectionColumn) { if (node->style.flexDirection == CSSFlexDirectionColumn) {
printf("flexDirection: 'column', "); gLogger("flexDirection: 'column', ");
} else if (node->style.flexDirection == CSSFlexDirectionColumnReverse) { } else if (node->style.flexDirection == CSSFlexDirectionColumnReverse) {
printf("flexDirection: 'column-reverse', "); gLogger("flexDirection: 'column-reverse', ");
} else if (node->style.flexDirection == CSSFlexDirectionRow) { } else if (node->style.flexDirection == CSSFlexDirectionRow) {
printf("flexDirection: 'row', "); gLogger("flexDirection: 'row', ");
} else if (node->style.flexDirection == CSSFlexDirectionRowReverse) { } else if (node->style.flexDirection == CSSFlexDirectionRowReverse) {
printf("flexDirection: 'row-reverse', "); gLogger("flexDirection: 'row-reverse', ");
} }
if (node->style.justifyContent == CSSJustifyCenter) { if (node->style.justifyContent == CSSJustifyCenter) {
printf("justifyContent: 'center', "); gLogger("justifyContent: 'center', ");
} else if (node->style.justifyContent == CSSJustifyFlexEnd) { } else if (node->style.justifyContent == CSSJustifyFlexEnd) {
printf("justifyContent: 'flex-end', "); gLogger("justifyContent: 'flex-end', ");
} else if (node->style.justifyContent == CSSJustifySpaceAround) { } else if (node->style.justifyContent == CSSJustifySpaceAround) {
printf("justifyContent: 'space-around', "); gLogger("justifyContent: 'space-around', ");
} else if (node->style.justifyContent == CSSJustifySpaceBetween) { } else if (node->style.justifyContent == CSSJustifySpaceBetween) {
printf("justifyContent: 'space-between', "); gLogger("justifyContent: 'space-between', ");
} }
if (node->style.alignItems == CSSAlignCenter) { if (node->style.alignItems == CSSAlignCenter) {
printf("alignItems: 'center', "); gLogger("alignItems: 'center', ");
} else if (node->style.alignItems == CSSAlignFlexEnd) { } else if (node->style.alignItems == CSSAlignFlexEnd) {
printf("alignItems: 'flex-end', "); gLogger("alignItems: 'flex-end', ");
} else if (node->style.alignItems == CSSAlignStretch) { } else if (node->style.alignItems == CSSAlignStretch) {
printf("alignItems: 'stretch', "); gLogger("alignItems: 'stretch', ");
} }
if (node->style.alignContent == CSSAlignCenter) { if (node->style.alignContent == CSSAlignCenter) {
printf("alignContent: 'center', "); gLogger("alignContent: 'center', ");
} else if (node->style.alignContent == CSSAlignFlexEnd) { } else if (node->style.alignContent == CSSAlignFlexEnd) {
printf("alignContent: 'flex-end', "); gLogger("alignContent: 'flex-end', ");
} else if (node->style.alignContent == CSSAlignStretch) { } else if (node->style.alignContent == CSSAlignStretch) {
printf("alignContent: 'stretch', "); gLogger("alignContent: 'stretch', ");
} }
if (node->style.alignSelf == CSSAlignFlexStart) { if (node->style.alignSelf == CSSAlignFlexStart) {
printf("alignSelf: 'flex-start', "); gLogger("alignSelf: 'flex-start', ");
} else if (node->style.alignSelf == CSSAlignCenter) { } else if (node->style.alignSelf == CSSAlignCenter) {
printf("alignSelf: 'center', "); gLogger("alignSelf: 'center', ");
} else if (node->style.alignSelf == CSSAlignFlexEnd) { } else if (node->style.alignSelf == CSSAlignFlexEnd) {
printf("alignSelf: 'flex-end', "); gLogger("alignSelf: 'flex-end', ");
} else if (node->style.alignSelf == CSSAlignStretch) { } else if (node->style.alignSelf == CSSAlignStretch) {
printf("alignSelf: 'stretch', "); gLogger("alignSelf: 'stretch', ");
} }
printNumberIfNotUndefined("flexGrow", node->style.flexGrow); printNumberIfNotUndefined("flexGrow", node->style.flexGrow);
@@ -465,11 +467,11 @@ _CSSNodePrint(const CSSNodeRef node, const CSSPrintOptions options, const uint32
printNumberIfNotUndefined("flexBasis", node->style.flexBasis); printNumberIfNotUndefined("flexBasis", node->style.flexBasis);
if (node->style.overflow == CSSOverflowHidden) { if (node->style.overflow == CSSOverflowHidden) {
printf("overflow: 'hidden', "); gLogger("overflow: 'hidden', ");
} else if (node->style.overflow == CSSOverflowVisible) { } else if (node->style.overflow == CSSOverflowVisible) {
printf("overflow: 'visible', "); gLogger("overflow: 'visible', ");
} else if (node->style.overflow == CSSOverflowScroll) { } else if (node->style.overflow == CSSOverflowScroll) {
printf("overflow: 'scroll', "); gLogger("overflow: 'scroll', ");
} }
if (eqFour(node->style.margin)) { if (eqFour(node->style.margin)) {
@@ -518,7 +520,7 @@ _CSSNodePrint(const CSSNodeRef node, const CSSPrintOptions options, const uint32
printNumberIfNotUndefined("minHeight", node->style.minDimensions[CSSDimensionHeight]); printNumberIfNotUndefined("minHeight", node->style.minDimensions[CSSDimensionHeight]);
if (node->style.positionType == CSSPositionTypeAbsolute) { if (node->style.positionType == CSSPositionTypeAbsolute) {
printf("position: 'absolute', "); gLogger("position: 'absolute', ");
} }
printNumberIfNotUndefined("left", printNumberIfNotUndefined("left",
@@ -533,14 +535,14 @@ _CSSNodePrint(const CSSNodeRef node, const CSSPrintOptions options, const uint32
const uint32_t childCount = CSSNodeListCount(node->children); const uint32_t childCount = CSSNodeListCount(node->children);
if (options & CSSPrintOptionsChildren && childCount > 0) { if (options & CSSPrintOptionsChildren && childCount > 0) {
printf("children: [\n"); gLogger("children: [\n");
for (uint32_t i = 0; i < childCount; i++) { for (uint32_t i = 0; i < childCount; i++) {
_CSSNodePrint(CSSNodeGetChild(node, i), options, level + 1); _CSSNodePrint(CSSNodeGetChild(node, i), options, level + 1);
} }
indent(level); indent(level);
printf("]},\n"); gLogger("]},\n");
} else { } else {
printf("},\n"); gLogger("},\n");
} }
} }
@@ -2363,6 +2365,10 @@ void CSSNodeCalculateLayout(const CSSNodeRef node,
} }
} }
void CSSLayoutSetLogger(CSSLogger logger) {
gLogger = logger;
}
#ifdef CSS_ASSERT_FAIL_ENABLED #ifdef CSS_ASSERT_FAIL_ENABLED
static CSSAssertFailFunc gAssertFailFunc; static CSSAssertFailFunc gAssertFailFunc;

View File

@@ -11,6 +11,7 @@
#include <assert.h> #include <assert.h>
#include <math.h> #include <math.h>
#include <stdarg.h>
#include <stdint.h> #include <stdint.h>
#include <stdio.h> #include <stdio.h>
#include <stdlib.h> #include <stdlib.h>
@@ -121,6 +122,7 @@ typedef CSSSize (*CSSMeasureFunc)(void *context,
float height, float height,
CSSMeasureMode heightMode); CSSMeasureMode heightMode);
typedef void (*CSSPrintFunc)(void *context); typedef void (*CSSPrintFunc)(void *context);
typedef int (*CSSLogger)(const char *format, ...);
#ifdef CSS_ASSERT_FAIL_ENABLED #ifdef CSS_ASSERT_FAIL_ENABLED
typedef void (*CSSAssertFailFunc)(const char *message); typedef void (*CSSAssertFailFunc)(const char *message);
@@ -210,6 +212,8 @@ CSS_NODE_LAYOUT_PROPERTY(float, Width);
CSS_NODE_LAYOUT_PROPERTY(float, Height); CSS_NODE_LAYOUT_PROPERTY(float, Height);
CSS_NODE_LAYOUT_PROPERTY(CSSDirection, Direction); CSS_NODE_LAYOUT_PROPERTY(CSSDirection, Direction);
WIN_EXPORT void CSSLayoutSetLogger(CSSLogger logger);
#ifdef CSS_ASSERT_FAIL_ENABLED #ifdef CSS_ASSERT_FAIL_ENABLED
// Assert // Assert
WIN_EXPORT void CSSAssertSetFailFunc(CSSAssertFailFunc func); WIN_EXPORT void CSSAssertSetFailFunc(CSSAssertFailFunc func);

View File

@@ -0,0 +1,30 @@
/**
* Copyright (c) 2014-present, Facebook, Inc.
* All rights reserved.
*
* This source code is licensed under the BSD-style license found in the
* LICENSE file in the root directory of this source tree. An additional grant
* of patent rights can be found in the PATENTS file in the same directory.
*/
#include "CSSInterop.h"
static CSSInteropLoggerFunc gManagedFunc;
static int unmanagedLogger(const char *format, ...) {
int result = 0;
if (gManagedFunc) {
va_list args;
va_start(args, format);
char buffer[256];
result = vsnprintf(buffer, sizeof(buffer), format, args);
(*gManagedFunc)(buffer);
va_end(args);
}
return result;
}
void CSSInteropSetLogger(CSSInteropLoggerFunc managedFunc) {
gManagedFunc = managedFunc;
CSSLayoutSetLogger(&unmanagedLogger);
}

View File

@@ -1,4 +1,4 @@
/** /**
* Copyright (c) 2014-present, Facebook, Inc. * Copyright (c) 2014-present, Facebook, Inc.
* All rights reserved. * All rights reserved.
* *
@@ -7,9 +7,14 @@
* of patent rights can be found in the PATENTS file in the same directory. * of patent rights can be found in the PATENTS file in the same directory.
*/ */
using System; #pragma once
namespace Facebook.CSSLayout #include <CSSLayout/CSSLayout.h>
{
public delegate void CSSPrintFunc(IntPtr context); CSS_EXTERN_C_BEGIN
}
typedef void (*CSSInteropLoggerFunc)(const char *message);
WIN_EXPORT void CSSInteropSetLogger(CSSInteropLoggerFunc managedFunc);
CSS_EXTERN_C_END

View File

@@ -1,177 +1,183 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<Project DefaultTargets="Build" ToolsVersion="14.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003"> <Project DefaultTargets="Build" ToolsVersion="14.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<ItemGroup Label="ProjectConfigurations"> <ItemGroup Label="ProjectConfigurations">
<ProjectConfiguration Include="Debug|Win32"> <ProjectConfiguration Include="Debug|Win32">
<Configuration>Debug</Configuration> <Configuration>Debug</Configuration>
<Platform>Win32</Platform> <Platform>Win32</Platform>
</ProjectConfiguration> </ProjectConfiguration>
<ProjectConfiguration Include="Release|Win32"> <ProjectConfiguration Include="Release|Win32">
<Configuration>Release</Configuration> <Configuration>Release</Configuration>
<Platform>Win32</Platform> <Platform>Win32</Platform>
</ProjectConfiguration> </ProjectConfiguration>
<ProjectConfiguration Include="Debug|x64"> <ProjectConfiguration Include="Debug|x64">
<Configuration>Debug</Configuration> <Configuration>Debug</Configuration>
<Platform>x64</Platform> <Platform>x64</Platform>
</ProjectConfiguration> </ProjectConfiguration>
<ProjectConfiguration Include="Release|x64"> <ProjectConfiguration Include="Release|x64">
<Configuration>Release</Configuration> <Configuration>Release</Configuration>
<Platform>x64</Platform> <Platform>x64</Platform>
</ProjectConfiguration> </ProjectConfiguration>
</ItemGroup> </ItemGroup>
<PropertyGroup Label="Globals"> <PropertyGroup Label="Globals">
<ProjectGuid>{0446C86B-F47B-4C46-B673-C7AE0CFF35D5}</ProjectGuid> <ProjectGuid>{0446C86B-F47B-4C46-B673-C7AE0CFF35D5}</ProjectGuid>
<Keyword>Win32Proj</Keyword> <Keyword>Win32Proj</Keyword>
<RootNamespace>CSSLayout</RootNamespace> <RootNamespace>CSSLayout</RootNamespace>
<WindowsTargetPlatformVersion>10.0.10586.0</WindowsTargetPlatformVersion> <WindowsTargetPlatformVersion>10.0.14393.0</WindowsTargetPlatformVersion>
</PropertyGroup> </PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" /> <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">
<ConfigurationType>DynamicLibrary</ConfigurationType> <ConfigurationType>DynamicLibrary</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries> <UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset> <PlatformToolset>v140</PlatformToolset>
<CharacterSet>Unicode</CharacterSet> <CharacterSet>Unicode</CharacterSet>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">
<ConfigurationType>DynamicLibrary</ConfigurationType> <ConfigurationType>DynamicLibrary</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries> <UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset> <PlatformToolset>v140</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization> <WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>Unicode</CharacterSet> <CharacterSet>Unicode</CharacterSet>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'" Label="Configuration">
<ConfigurationType>DynamicLibrary</ConfigurationType> <ConfigurationType>DynamicLibrary</ConfigurationType>
<UseDebugLibraries>true</UseDebugLibraries> <UseDebugLibraries>true</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset> <PlatformToolset>v140</PlatformToolset>
<CharacterSet>Unicode</CharacterSet> <CharacterSet>Unicode</CharacterSet>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'" Label="Configuration">
<ConfigurationType>DynamicLibrary</ConfigurationType> <ConfigurationType>DynamicLibrary</ConfigurationType>
<UseDebugLibraries>false</UseDebugLibraries> <UseDebugLibraries>false</UseDebugLibraries>
<PlatformToolset>v140</PlatformToolset> <PlatformToolset>v140</PlatformToolset>
<WholeProgramOptimization>true</WholeProgramOptimization> <WholeProgramOptimization>true</WholeProgramOptimization>
<CharacterSet>Unicode</CharacterSet> <CharacterSet>Unicode</CharacterSet>
</PropertyGroup> </PropertyGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" /> <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />
<ImportGroup Label="ExtensionSettings"> <ImportGroup Label="ExtensionSettings">
</ImportGroup> </ImportGroup>
<ImportGroup Label="Shared"> <ImportGroup Label="Shared">
</ImportGroup> </ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'"> <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" /> <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup> </ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'"> <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" /> <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup> </ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|x64'"> <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" /> <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup> </ImportGroup>
<ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|x64'"> <ImportGroup Label="PropertySheets" Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" /> <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />
</ImportGroup> </ImportGroup>
<PropertyGroup Label="UserMacros" /> <PropertyGroup Label="UserMacros" />
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<LinkIncremental>true</LinkIncremental> <LinkIncremental>true</LinkIncremental>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<LinkIncremental>true</LinkIncremental> <LinkIncremental>true</LinkIncremental>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<LinkIncremental>false</LinkIncremental> <LinkIncremental>false</LinkIncremental>
</PropertyGroup> </PropertyGroup>
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'"> <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
<LinkIncremental>false</LinkIncremental> <LinkIncremental>false</LinkIncremental>
</PropertyGroup> </PropertyGroup>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'"> <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
<ClCompile> <ClCompile>
<PrecompiledHeader> <PrecompiledHeader>
</PrecompiledHeader> </PrecompiledHeader>
<WarningLevel>Level3</WarningLevel> <WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization> <Optimization>Disabled</Optimization>
<PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;_USRDLL;CSSLAYOUT_EXPORTS;CSS_ASSERT_FAIL_ENABLED;FB_ASSERTIONS_ENABLED=0;%(PreprocessorDefinitions)</PreprocessorDefinitions> <PreprocessorDefinitions>WIN32;_DEBUG;_WINDOWS;_USRDLL;CSSLAYOUT_EXPORTS;CSS_ASSERT_FAIL_ENABLED;FB_ASSERTIONS_ENABLED=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<SDLCheck>true</SDLCheck> <SDLCheck>true</SDLCheck>
</ClCompile> <AdditionalIncludeDirectories>$(ProjectDir)..\..\;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<Link> </ClCompile>
<SubSystem>Windows</SubSystem> <Link>
<GenerateDebugInformation>true</GenerateDebugInformation> <SubSystem>Windows</SubSystem>
</Link> <GenerateDebugInformation>true</GenerateDebugInformation>
</ItemDefinitionGroup> </Link>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'"> </ItemDefinitionGroup>
<ClCompile> <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
<PrecompiledHeader> <ClCompile>
</PrecompiledHeader> <PrecompiledHeader>
<WarningLevel>Level3</WarningLevel> </PrecompiledHeader>
<Optimization>Disabled</Optimization> <WarningLevel>Level3</WarningLevel>
<PreprocessorDefinitions>_DEBUG;_WINDOWS;_USRDLL;CSSLAYOUT_EXPORTS;CSS_ASSERT_FAIL_ENABLED;FB_ASSERTIONS_ENABLED=0;%(PreprocessorDefinitions)</PreprocessorDefinitions> <Optimization>Disabled</Optimization>
<SDLCheck>true</SDLCheck> <PreprocessorDefinitions>_DEBUG;_WINDOWS;_USRDLL;CSSLAYOUT_EXPORTS;CSS_ASSERT_FAIL_ENABLED;FB_ASSERTIONS_ENABLED=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>
</ClCompile> <SDLCheck>true</SDLCheck>
<Link> <AdditionalIncludeDirectories>$(ProjectDir)..\..\;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<SubSystem>Windows</SubSystem> </ClCompile>
<GenerateDebugInformation>true</GenerateDebugInformation> <Link>
</Link> <SubSystem>Windows</SubSystem>
</ItemDefinitionGroup> <GenerateDebugInformation>true</GenerateDebugInformation>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'"> </Link>
<ClCompile> </ItemDefinitionGroup>
<WarningLevel>Level3</WarningLevel> <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
<PrecompiledHeader> <ClCompile>
</PrecompiledHeader> <WarningLevel>Level3</WarningLevel>
<Optimization>MaxSpeed</Optimization> <PrecompiledHeader>
<FunctionLevelLinking>true</FunctionLevelLinking> </PrecompiledHeader>
<IntrinsicFunctions>true</IntrinsicFunctions> <Optimization>MaxSpeed</Optimization>
<PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;_USRDLL;CSSLAYOUT_EXPORTS;CSS_ASSERT_FAIL_ENABLED;FB_ASSERTIONS_ENABLED=0;%(PreprocessorDefinitions)</PreprocessorDefinitions> <FunctionLevelLinking>true</FunctionLevelLinking>
<SDLCheck>true</SDLCheck> <IntrinsicFunctions>true</IntrinsicFunctions>
</ClCompile> <PreprocessorDefinitions>WIN32;NDEBUG;_WINDOWS;_USRDLL;CSSLAYOUT_EXPORTS;CSS_ASSERT_FAIL_ENABLED;FB_ASSERTIONS_ENABLED=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<Link> <SDLCheck>true</SDLCheck>
<SubSystem>Windows</SubSystem> <AdditionalIncludeDirectories>$(ProjectDir)..\..\;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<EnableCOMDATFolding>true</EnableCOMDATFolding> </ClCompile>
<OptimizeReferences>true</OptimizeReferences> <Link>
<GenerateDebugInformation>true</GenerateDebugInformation> <SubSystem>Windows</SubSystem>
</Link> <EnableCOMDATFolding>true</EnableCOMDATFolding>
</ItemDefinitionGroup> <OptimizeReferences>true</OptimizeReferences>
<ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'"> <GenerateDebugInformation>true</GenerateDebugInformation>
<ClCompile> </Link>
<WarningLevel>Level3</WarningLevel> </ItemDefinitionGroup>
<PrecompiledHeader> <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
</PrecompiledHeader> <ClCompile>
<Optimization>MaxSpeed</Optimization> <WarningLevel>Level3</WarningLevel>
<FunctionLevelLinking>true</FunctionLevelLinking> <PrecompiledHeader>
<IntrinsicFunctions>true</IntrinsicFunctions> </PrecompiledHeader>
<PreprocessorDefinitions>NDEBUG;_WINDOWS;_USRDLL;CSSLAYOUT_EXPORTS;CSS_ASSERT_FAIL_ENABLED;FB_ASSERTIONS_ENABLED=0;%(PreprocessorDefinitions)</PreprocessorDefinitions> <Optimization>MaxSpeed</Optimization>
<SDLCheck>true</SDLCheck> <FunctionLevelLinking>true</FunctionLevelLinking>
</ClCompile> <IntrinsicFunctions>true</IntrinsicFunctions>
<Link> <PreprocessorDefinitions>NDEBUG;_WINDOWS;_USRDLL;CSSLAYOUT_EXPORTS;CSS_ASSERT_FAIL_ENABLED;FB_ASSERTIONS_ENABLED=0;%(PreprocessorDefinitions)</PreprocessorDefinitions>
<SubSystem>Windows</SubSystem> <SDLCheck>true</SDLCheck>
<EnableCOMDATFolding>true</EnableCOMDATFolding> <AdditionalIncludeDirectories>$(ProjectDir)..\..\;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>
<OptimizeReferences>true</OptimizeReferences> </ClCompile>
<GenerateDebugInformation>true</GenerateDebugInformation> <Link>
</Link> <SubSystem>Windows</SubSystem>
</ItemDefinitionGroup> <EnableCOMDATFolding>true</EnableCOMDATFolding>
<ItemGroup> <OptimizeReferences>true</OptimizeReferences>
<ClInclude Include="..\..\CSSLayout\CSSLayout.h" /> <GenerateDebugInformation>true</GenerateDebugInformation>
<ClInclude Include="..\..\CSSLayout\CSSMacros.h" /> </Link>
<ClInclude Include="..\..\CSSLayout\CSSNodeList.h" /> </ItemDefinitionGroup>
<ClInclude Include="stdafx.h" /> <ItemGroup>
<ClInclude Include="targetver.h" /> <ClInclude Include="..\..\CSSLayout\CSSLayout.h" />
</ItemGroup> <ClInclude Include="..\..\CSSLayout\CSSMacros.h" />
<ItemGroup> <ClInclude Include="..\..\CSSLayout\CSSNodeList.h" />
<ClCompile Include="..\..\CSSLayout\CSSLayout.c" /> <ClInclude Include="CSSInterop.h" />
<ClCompile Include="..\..\CSSLayout\CSSNodeList.c" /> <ClInclude Include="stdafx.h" />
<ClCompile Include="dllmain.cpp"> <ClInclude Include="targetver.h" />
<CompileAsManaged Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">false</CompileAsManaged> </ItemGroup>
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'"> <ItemGroup>
</PrecompiledHeader> <ClCompile Include="..\..\CSSLayout\CSSLayout.c" />
<CompileAsManaged Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">false</CompileAsManaged> <ClCompile Include="..\..\CSSLayout\CSSNodeList.c" />
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|x64'"> <ClCompile Include="CSSInterop.cpp" />
</PrecompiledHeader> <ClCompile Include="dllmain.cpp">
<CompileAsManaged Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</CompileAsManaged> <CompileAsManaged Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">false</CompileAsManaged>
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|Win32'"> <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">
</PrecompiledHeader> </PrecompiledHeader>
<CompileAsManaged Condition="'$(Configuration)|$(Platform)'=='Release|x64'">false</CompileAsManaged> <CompileAsManaged Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">false</CompileAsManaged>
<PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|x64'"> <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">
</PrecompiledHeader> </PrecompiledHeader>
</ClCompile> <CompileAsManaged Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</CompileAsManaged>
<ClCompile Include="stdafx.cpp" /> <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
</ItemGroup> </PrecompiledHeader>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" /> <CompileAsManaged Condition="'$(Configuration)|$(Platform)'=='Release|x64'">false</CompileAsManaged>
<ImportGroup Label="ExtensionTargets"> <PrecompiledHeader Condition="'$(Configuration)|$(Platform)'=='Release|x64'">
</ImportGroup> </PrecompiledHeader>
</Project> </ClCompile>
<ClCompile Include="stdafx.cpp" />
</ItemGroup>
<Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />
<ImportGroup Label="ExtensionTargets">
</ImportGroup>
</Project>

6
csharp/CSSLayout/CSSLayout.vcxproj.filters Normal file → Executable file
View File

@@ -30,6 +30,9 @@
<ClInclude Include="..\..\CSSLayout\CSSNodeList.h"> <ClInclude Include="..\..\CSSLayout\CSSNodeList.h">
<Filter>Header Files</Filter> <Filter>Header Files</Filter>
</ClInclude> </ClInclude>
<ClInclude Include="CSSInterop.h">
<Filter>Header Files</Filter>
</ClInclude>
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<ClCompile Include="stdafx.cpp"> <ClCompile Include="stdafx.cpp">
@@ -44,5 +47,8 @@
<ClCompile Include="..\..\CSSLayout\CSSNodeList.c"> <ClCompile Include="..\..\CSSLayout\CSSNodeList.c">
<Filter>Source Files</Filter> <Filter>Source Files</Filter>
</ClCompile> </ClCompile>
<ClCompile Include="CSSInterop.cpp">
<Filter>Source Files</Filter>
</ClCompile>
</ItemGroup> </ItemGroup>
</Project> </Project>

View File

@@ -16,14 +16,16 @@ namespace Facebook.CSSLayout
public delegate void FailFunc(string message); public delegate void FailFunc(string message);
private static bool _assertInitialized; private static bool _assertInitialized;
private static FailFunc _failFunc;
public static void Initialize() public static void Initialize()
{ {
if (!_assertInitialized) if (!_assertInitialized)
{ {
Native.CSSAssertSetFailFunc((message) => { _failFunc = (message) => {
throw new InvalidOperationException(message); throw new InvalidOperationException(message);
}); };
Native.CSSAssertSetFailFunc(_failFunc);
_assertInitialized = true; _assertInitialized = true;
} }
} }

View File

@@ -0,0 +1,38 @@
/**
* Copyright (c) 2014-present, Facebook, Inc.
* All rights reserved.
*
* This source code is licensed under the BSD-style license found in the
* LICENSE file in the root directory of this source tree. An additional grant
* of patent rights can be found in the PATENTS file in the same directory.
*/
using System;
namespace Facebook.CSSLayout
{
internal static class CSSLogger
{
public delegate void Func(string message);
private static bool _initialized;
private static Func _managedLogger = null;
public static Func Logger = null;
public static void Initialize()
{
if (!_initialized)
{
_managedLogger = (message) => {
if (Logger != null)
{
Logger(message);
}
};
Native.CSSInteropSetLogger(_managedLogger);
_initialized = true;
}
}
}
}

View File

@@ -11,6 +11,7 @@ using System;
using System.Collections; using System.Collections;
using System.Collections.Generic; using System.Collections.Generic;
using System.Runtime.InteropServices; using System.Runtime.InteropServices;
using System.Text;
namespace Facebook.CSSLayout namespace Facebook.CSSLayout
{ {
@@ -110,9 +111,9 @@ namespace Facebook.CSSLayout
} }
CSSAssert.Initialize(); CSSAssert.Initialize();
CSSLogger.Initialize();
_cssNode = Native.CSSNodeNew(); _cssNode = Native.CSSNodeNew();
_children = new List<CSSNode>(4); _children = new List<CSSNode>(4);
Native.CSSNodeSetPrintFunc(_cssNode, PrintInternal);
} }
public void Free() public void Free()
@@ -704,9 +705,14 @@ namespace Facebook.CSSLayout
return new CSSSize { width = measureResult.Width, height = measureResult.Height }; return new CSSSize { width = measureResult.Width, height = measureResult.Height };
} }
private void PrintInternal(IntPtr context) public string Print(CSSPrintOptions options = CSSPrintOptions.Layout|CSSPrintOptions.Style|CSSPrintOptions.Children)
{ {
System.Diagnostics.Debug.WriteLine(ToString()); AssertNativeInstance();
StringBuilder sb = new StringBuilder();
CSSLogger.Logger = (message) => {sb.Append(message);};
Native.CSSNodePrint(_cssNode, options);
CSSLogger.Logger = null;
return sb.ToString();
} }
public IEnumerator<CSSNode> GetEnumerator() public IEnumerator<CSSNode> GetEnumerator()

View File

@@ -20,6 +20,9 @@ namespace Facebook.CSSLayout
private const string DllName = "CSSLayout"; private const string DllName = "CSSLayout";
#endif #endif
[DllImport(DllName)]
public static extern void CSSInteropSetLogger(CSSLogger.Func func);
[DllImport(DllName)] [DllImport(DllName)]
public static extern void CSSAssertSetFailFunc(CSSAssert.FailFunc func); public static extern void CSSAssertSetFailFunc(CSSAssert.FailFunc func);
@@ -81,12 +84,6 @@ namespace Facebook.CSSLayout
[DllImport(DllName)] [DllImport(DllName)]
public static extern CSSMeasureFunc CSSNodeGetMeasureFunc(IntPtr node); public static extern CSSMeasureFunc CSSNodeGetMeasureFunc(IntPtr node);
[DllImport(DllName)]
public static extern void CSSNodeSetPrintFunc(IntPtr node, CSSPrintFunc printFunc);
[DllImport(DllName)]
public static extern CSSPrintFunc CSSNodeGePrintFunc(IntPtr node);
[DllImport(DllName)] [DllImport(DllName)]
public static extern void CSSNodeSetIsTextnode(IntPtr node, [MarshalAs(UnmanagedType.I1)] bool isTextNode); public static extern void CSSNodeSetIsTextnode(IntPtr node, [MarshalAs(UnmanagedType.I1)] bool isTextNode);

View File

@@ -178,6 +178,24 @@ namespace Facebook.CSSLayout
Assert.AreEqual(150, (int)node.LayoutHeight); Assert.AreEqual(150, (int)node.LayoutHeight);
} }
[Test]
public void TestPrint()
{
CSSNode parent = new CSSNode();
parent.StyleWidth = 100;
parent.StyleHeight = 120;
CSSNode child0 = new CSSNode();
child0.StyleWidth = 30;
child0.StyleHeight = 40;
CSSNode child1 = new CSSNode();
child1.StyleWidth = 35;
child1.StyleHeight = 45;
parent.Insert(0, child0);
parent.Insert(0, child1);
parent.CalculateLayout();
Assert.AreEqual(parent.Print(), "{layout: {width: 100, height: 120, top: 0, left: 0}, flexDirection: 'column', alignItems: 'stretch', flexGrow: 0, flexShrink: 0, overflow: 'visible', width: 100, height: 120, children: [\n {layout: {width: 35, height: 45, top: 0, left: 0}, flexDirection: 'column', alignItems: 'stretch', flexGrow: 0, flexShrink: 0, overflow: 'visible', width: 35, height: 45, },\n {layout: {width: 30, height: 40, top: 45, left: 0}, flexDirection: 'column', alignItems: 'stretch', flexGrow: 0, flexShrink: 0, overflow: 'visible', width: 30, height: 40, },\n]},\n");
}
private void ForceGC() private void ForceGC()
{ {
GC.Collect(GC.MaxGeneration); GC.Collect(GC.MaxGeneration);