Skip to content

Commit

Permalink
Implement single frame renderer
Browse files Browse the repository at this point in the history
  • Loading branch information
Achilleas Anagnostopoulos committed Sep 8, 2016
1 parent d70a8a5 commit 71b3c03
Show file tree
Hide file tree
Showing 5 changed files with 421 additions and 158 deletions.
90 changes: 90 additions & 0 deletions cmd/render.go
Original file line number Diff line number Diff line change
@@ -1,5 +1,18 @@
package cmd

import (
"bytes"
"errors"
"fmt"

"github.com/achilleasa/go-pathtrace/asset/scene/reader"
"github.com/achilleasa/go-pathtrace/renderer"
"github.com/achilleasa/go-pathtrace/tracer"
"github.com/achilleasa/go-pathtrace/tracer/opencl"
"github.com/olekukonko/tablewriter"
"github.com/urfave/cli"
)

const (
// Coefficients for converting delta cursor movements to yaw/pitch camera angles.
mouseSensitivityX float32 = 0.005
Expand All @@ -9,6 +22,83 @@ const (
cameraMoveSpeed float32 = 0.05
)

// Render a still frame.
func RenderFrame(ctx *cli.Context) error {
setupLogging(ctx)

opts := renderer.Options{
FrameW: uint32(ctx.Int("width")),
FrameH: uint32(ctx.Int("height")),
SamplesPerPixel: uint32(ctx.Int("spp")),
Exposure: float32(ctx.Float64("exposure")),
NumBounces: uint32(ctx.Int("num-bounces")),
MinBouncesForRR: uint32(ctx.Int("rr-bounces")),
//
BlackListedDevices: ctx.StringSlice("blacklist"),
ForcePrimaryDevice: ctx.String("force-primary"),
}

if opts.MinBouncesForRR == 0 || opts.MinBouncesForRR >= opts.NumBounces {
logger.Notice("disabling RR for path elimination")
opts.MinBouncesForRR = opts.NumBounces + 1
}

// Load scene
if ctx.NArg() != 1 {
return errors.New("missing scene file argument")
}

sc, err := reader.ReadScene(ctx.Args().First())
if err != nil {
return err
}

// Update projection matrix
sc.Camera.SetupProjection(float32(opts.FrameW) / float32(opts.FrameH))

// Setup tracing pipeline
pipeline := opencl.DefaultPipeline(opencl.NoDebug)
pipeline.PostProcess = append(pipeline.PostProcess, opencl.SaveFrameBuffer(ctx.String("out")))

// Create renderer
r, err := renderer.NewDefault(sc, tracer.NaiveScheduler(), pipeline, opts)
if err != nil {
return err
}
defer r.Close()

_, err = r.Render(0)
if err != nil {
return err
}

// Display stats
displayFrameStats(r.Stats())

return err
}

func displayFrameStats(stats renderer.FrameStats) {
var buf bytes.Buffer
table := tablewriter.NewWriter(&buf)
table.SetAutoFormatHeaders(false)
table.SetAutoWrapText(false)
table.SetHeader([]string{"Device", "Primary", "Block height", "% of frame", "Render time"})
for _, stat := range stats.Tracers {
table.Append([]string{
stat.Id,
fmt.Sprintf("%t", stat.IsPrimary),
fmt.Sprintf("%d", stat.BlockH),
fmt.Sprintf("%02.1f %%", stat.FramePercent),
fmt.Sprintf("%s", stat.RenderTime),
})
}
table.SetFooter([]string{"", "", "", "TOTAL", fmt.Sprintf("%s", stats.RenderTime)})

table.Render()
logger.Noticef("frame statistics\n%s", buf.String())
}

/*
// Return the available opencl devices after applying the blacklist filters.
func filteredDeviceList(ctx *cli.Context) []opencl.Device {
Expand Down
60 changes: 46 additions & 14 deletions main.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,16 @@ import (
"github.com/urfave/cli"
)

var (
sceneCompileHelp = `
Parse a scene definition from a wavefront obj file, build a BVH tree to optimize
ray intersection tests and package scene assets in a GPU-friendly format.
The optimized scene data is then written to a zip archive which can be supplied
as an argument to the render commands.
`
)

func main() {
cli.VersionFlag = cli.BoolFlag{
Name: "version",
Expand All @@ -30,16 +40,22 @@ func main() {
}
app.Commands = []cli.Command{
{
Name: "compile",
Usage: "compile text scene representation into a binary compressed format",
Description: `
Parse a scene definition from a wavefront obj file, build a BVH tree to optimize
ray intersection tests and package scene elements in a GPU-friendly format.
The optimized scene data is then written to a zip archive which can be supplied
as an argument to the render command.`,
ArgsUsage: "scene_file1.obj scene_file2.obj ...",
Action: cmd.CompileScene,
Name: "scene",
Subcommands: []cli.Command{
{
Name: "compile",
Usage: "compile text scene representation into a binary compressed format",
Description: sceneCompileHelp,
ArgsUsage: "scene_file1.obj scene_file2.obj ...",
Action: cmd.CompileScene,
},
{
Name: "info",
Usage: "print the size of the various compiled scene assets",
ArgsUsage: "scene_file.zip",
Action: cmd.ShowSceneInfo,
},
},
},
{
Name: "list-devices",
Expand All @@ -55,39 +71,55 @@ as an argument to the render command.`,
Name: "frame",
Usage: "render single frame",
Description: `Render a single frame.`,
ArgsUsage: "scene_file.zip or scene_file.obj",
Flags: []cli.Flag{
cli.IntFlag{
Name: "width",
Value: 512,
Value: 1024,
Usage: "frame width",
},
cli.IntFlag{
Name: "height",
Value: 512,
Value: 1024,
Usage: "frame height",
},
cli.IntFlag{
Name: "spp",
Value: 16,
Usage: "samples per pixel",
},
cli.IntFlag{
Name: "num-bounces, nb",
Value: 5,
Usage: "number of indirect ray bounces",
},
cli.IntFlag{
Name: "rr-bounces, nr",
Value: 3,
Usage: "number of indirect ray bounces before applying RR (disabled if 0 or >= than num-bounces)",
},
cli.Float64Flag{
Name: "exposure",
Value: 1.0,
Value: 1.2,
Usage: "camera exposure for tone-mapping",
},
cli.StringSliceFlag{
Name: "blacklist, b",
Value: &cli.StringSlice{},
Usage: "blacklist opencl device whose names contain this value",
},
cli.StringFlag{
Name: "force-primary",
Value: "",
Usage: "force a particular device name as the primary device",
},
cli.StringFlag{
Name: "out, o",
Value: "frame.png",
Usage: "image filename for the rendered frame",
},
},
// Action: cmd.RenderFrame,
Action: cmd.RenderFrame,
},
{
Name: "interactive",
Expand Down
23 changes: 23 additions & 0 deletions renderer/options.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package renderer

type Options struct {
// Frame dims.
FrameW uint32
FrameH uint32

// Number of indirect bounces.
NumBounces uint32

// Min bounces before applying russian roulette for path elimination.
MinBouncesForRR uint32

// Number of samples.
SamplesPerPixel uint32

// Exposure for tonemapping.
Exposure float32

// Device selection.
BlackListedDevices []string
ForcePrimaryDevice string
}
Loading

0 comments on commit 71b3c03

Please sign in to comment.