From: Good Guy Date: Sun, 16 Jun 2019 18:45:39 +0000 (-0600) Subject: configure.ac add with-cuda/nv, update cakewalk theme, add cuda/plugins=mandel+nbody... X-Git-Tag: 2019-08~37 X-Git-Url: https://cinelerra-gg.org/git/?a=commitdiff_plain;h=b1649fe7b38cfb4bbec58b19fb8dda2daa0ce520;p=goodguy%2Fcinelerra.git configure.ac add with-cuda/nv, update cakewalk theme, add cuda/plugins=mandel+nbody, add nvenc formats --- diff --git a/cinelerra-5.1/configure.ac b/cinelerra-5.1/configure.ac index 90048a29..0f8c6e41 100644 --- a/cinelerra-5.1/configure.ac +++ b/cinelerra-5.1/configure.ac @@ -58,6 +58,8 @@ CHECK_WITH([thirdparty],[use thirdparty build],[CIN_3RDPARTY],[yes]) CHECK_WITH([shuttle],[shuttle device],[SHUTTLE],[yes]) CHECK_WITH([vaapi],[video acceleration api],[VAAPI],[yes]) CHECK_WITH([vdpau],[video decode+presentation api for unix],[VDPAU],[yes]) +CHECK_WITH([nv],[video acceleration api],[NV],[yes]) +CHECK_WITH([cuda],[video decode+presentation api for unix],[CUDA],[auto]) if test "x$WANT_LV2" != "xno"; then GTK2_LIBS=`pkg-config --libs gtk+-2.0` @@ -414,6 +416,11 @@ PKG_3RD([libwebp],[auto], [ usr/local/lib*/libwebp*.a ], [ usr/local/include ]) +PKG_3RD([ffnvcodec],[auto], + [ffnvcodec], + [ ], + [ . ]) + AC_SUBST(STATIC_PKGS) AC_DEFUN([CHECK_ENABLE], [ @@ -589,6 +596,7 @@ if test "x$WANT_VAAPI" != "xno" -a "x$HAVE_VAAPI" = "xyes"; then CHECK_HEADERS([vaapi_drm], [va drm headers], [va/va_drm.h]) CHECK_LIB([vaapi_drm], [va-drm], [vaGetDisplayDRM]) fi +#CHECK_LIB([NVENC], [nvidia-encode], [NvEncodeAPICreateInstance]) #if test "x$HAVE_mjpegtools" = "xyes"; then #CFG_CFLAGS+=" -I/usr/include/mjpegtools -I/usr/local/include/mjpegtools" @@ -606,7 +614,6 @@ AC_ARG_WITH(m4_tolower([$1]), if test "x$WANT_$1" = "xyes" ; then AC_MSG_ERROR([required for $1 support.]) fi - echo "=== want $1 Failed." WANT_$1=no elif test "x$WANT_$1" = "xauto" ; then WANT_$1=yes @@ -683,6 +690,9 @@ CHECK_WANT([LV2], [auto], [use lv2], [ CHECK_HEADERS([lv2], [suil headers], [suil/suil.h]) CFLAGS="$saved_CFLAGS"]) +CHECK_WANT([CUDA], [auto], [build cuda plugins], [ + CHECK_HEADERS([CUDA], [cuda sdk], [/usr/local/cuda/include/cuda.h])]) + CHECK_WANT([DL], [auto], [system has libdl], [ CHECK_LIB([DL], [dl], [dlopen])]) @@ -832,6 +842,7 @@ PKG_PROVIDE([sratom], [$WANT_LV2]) PKG_PROVIDE([serd], [$WANT_LV2]) PKG_PROVIDE([sord], [$WANT_LV2]) PKG_PROVIDE([suil], [$WANT_LV2]) +PKG_PROVIDE([ffnvcodec], [$WANT_NV]) if test "x$WANT_LV2" = "xyes"; then if test "x$HAVE_lv2" = "xyes" -a "x$BUILD_lilv" = "x0"; then @@ -884,6 +895,8 @@ echo " using: with-libzmpeg = $WANT_LIBZMPEG" echo " using: with-commerical = $WANT_COMMERCIAL" echo " using: with-vaapi = $WANT_VAAPI" echo " using: with-vdpau = $WANT_VDPAU" +echo " using: with-nv = $WANT_NV" +echo " using: with-cuda = $WANT_CUDA" echo "" echo " using: thirdparty build = $WANT_CIN_3RDPARTY" echo " using: single-user = $WANT_CINBIN_BUILD" @@ -920,6 +933,10 @@ if test "x$WANT_VDPAU" != "xno" -a "x$HAVE_VDPAU" = "xyes"; then WANT_VDPAU="yes" CFG_WANTS+=" VDPAU" fi +if test "x$WANT_NV" != "xno"; then + WANT_NV="yes" + CFG_WANTS+=" NV" +fi if test "x$HAVE_DL" = "xyes"; then EXTRA_LIBS+=' -ldl' diff --git a/cinelerra-5.1/ffmpeg/video/h264_nvenc.mp4 b/cinelerra-5.1/ffmpeg/video/h264_nvenc.mp4 new file mode 100644 index 00000000..d48bacd2 --- /dev/null +++ b/cinelerra-5.1/ffmpeg/video/h264_nvenc.mp4 @@ -0,0 +1,4 @@ +mp4 h264_nvenc +# encode for nvidia graphics hw only +preset medium +profile main diff --git a/cinelerra-5.1/ffmpeg/video/h265_nvenc.mp4 b/cinelerra-5.1/ffmpeg/video/h265_nvenc.mp4 new file mode 100644 index 00000000..784d8a60 --- /dev/null +++ b/cinelerra-5.1/ffmpeg/video/h265_nvenc.mp4 @@ -0,0 +1,4 @@ +mp4 hevc_nvenc +# encode for nvidia graphics hw only +preset medium +profile main diff --git a/cinelerra-5.1/plugin_cuda b/cinelerra-5.1/plugin_cuda new file mode 100644 index 00000000..10ee7faf --- /dev/null +++ b/cinelerra-5.1/plugin_cuda @@ -0,0 +1,32 @@ +#cuda compile + +CUDA_PATH ?= /usr/local/cuda-10.1 +TARGET_SIZE := 64 # 32 +HOST_COMPILER ?= g++ +NVCC := $(CUDA_PATH)/bin/nvcc -ccbin $(HOST_COMPILER) +NVCCFLAGS := -m${TARGET_SIZE} -Xcompiler -fPIC -Xcompiler -fno-omit-frame-pointer -g +LDFLAGS = -lcuda -L /usr/local/cuda/targets/x86_64-linux/lib -lcudart + +SMS ?= 30 35 37 50 52 60 61 70 75 +$(foreach sm,$(SMS),$(eval GENCODE_FLAGS += -gencode arch=compute_$(sm),code=sm_$(sm))) +HIGHEST_SM := $(lastword $(sort $(SMS))) +GENCODE_FLAGS += -gencode arch=compute_$(HIGHEST_SM),code=compute_$(HIGHEST_SM) + +# samples source access BEWARE! +# contains includes which conflict: search /usr/include first +CFLAGS += -I/usr/include -I/usr/local/cuda/samples +CFLAGS += -I/usr/local/cuda/samples/common/inc +CFLAGS += -I/usr/local/cuda/targets/x86_64-linux/include +CFLAGS += -Wno-unused-function + +INCLUDES += -I$(TOPDIR)/cinelerra -I$(TOPDIR)/guicast +INCLUDES += -I/usr/local/cuda/samples +INCLUDES += -I/usr/local/cuda/samples/common/inc +INCLUDES += -I/usr/local/cuda/targets/x86_64-linux/include + +CUFLAGS := $(INCLUDES) $(NVCCFLAGS) $(GENCODE_FLAGS) +$(shell mkdir -p $(OBJDIR)) +$(shell echo $(CUFLAGS) > $(OBJDIR)/cu_flags) + +$(OBJDIR)/%.o: %.cu + $(NVCC) `cat $(OBJDIR)/cu_flags` $(BFLAGS) -DMSGQUAL=$* -c $< -o $@ diff --git a/cinelerra-5.1/plugin_defs b/cinelerra-5.1/plugin_defs index 5890e213..afd04e88 100644 --- a/cinelerra-5.1/plugin_defs +++ b/cinelerra-5.1/plugin_defs @@ -15,6 +15,7 @@ themes := \ theme_suv \ theme_neophyte \ theme_unflat \ + theme_cakewalk \ plugin_dirs += video video := \ @@ -76,6 +77,8 @@ video := \ motionblur \ motion-cv \ motion-hv \ + mandelcuda \ + nbodycuda \ oil \ overlay \ perspective \ diff --git a/cinelerra-5.1/plugins/Makefile b/cinelerra-5.1/plugins/Makefile index 77292863..2bf29432 100644 --- a/cinelerra-5.1/plugins/Makefile +++ b/cinelerra-5.1/plugins/Makefile @@ -11,6 +11,9 @@ include $(TOPDIR)/opencv_build OPENCV_OBJS := findobj flowobj gaborobj moveobj stylizeobj puzzleobj $(OPENCV_OBJS): opencv endif +ifneq ($(WANT_CUDA), no) +CUDA_OBJS := mandelcuda nbodycuda +endif # burn must come before any other effecttv plugin # colors must come before any plugin @@ -18,6 +21,7 @@ endif # motion must come before perspective DIRS = $(OPENCV_OBJS) \ + $(CUDA_OBJS) \ 1080to480 \ 1080to540 \ 720to480 \ diff --git a/cinelerra-5.1/plugins/mandelcuda/.swp b/cinelerra-5.1/plugins/mandelcuda/.swp new file mode 100644 index 00000000..5d9b1b9c Binary files /dev/null and b/cinelerra-5.1/plugins/mandelcuda/.swp differ diff --git a/cinelerra-5.1/plugins/mandelcuda/Makefile b/cinelerra-5.1/plugins/mandelcuda/Makefile new file mode 100644 index 00000000..95d8587d --- /dev/null +++ b/cinelerra-5.1/plugins/mandelcuda/Makefile @@ -0,0 +1,17 @@ +TOPDIR?=../.. +include $(TOPDIR)/plugin_defs +include $(TOPDIR)/plugin_cuda + +PLUGIN = mandelcuda + +OBJS := \ + $(OBJDIR)/mandelbrot.o \ + $(OBJDIR)/mandelbrotwindow.o \ + $(OBJDIR)/mandelcuda.o \ + +include $(TOPDIR)/plugin_config + +$(OBJDIR)/mandelbrot.o: mandelbrot.C mandelbrot.h +$(OBJDIR)/mandelbrotwindow.o: mandelbrotwindow.C mandelbrotwindow.h +$(OBJDIR)/mandelcuda.o: mandelcuda.cu mandelcuda.h + diff --git a/cinelerra-5.1/plugins/mandelcuda/mandelbrot.C b/cinelerra-5.1/plugins/mandelcuda/mandelbrot.C new file mode 100644 index 00000000..693b867f --- /dev/null +++ b/cinelerra-5.1/plugins/mandelcuda/mandelbrot.C @@ -0,0 +1,303 @@ +/* + * CINELERRA + * Copyright (C) 1997-2014 Adam Williams + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + */ + +#include "clip.h" +#include "filexml.h" +#include "mandelbrot.h" +#include "mandelbrotwindow.h" +#include "language.h" +#include "mutex.h" + +#include "cwindow.h" +#include "cwindowgui.h" +#include "mwindow.h" +#include "pluginserver.h" +#include "playback3d.h" + +REGISTER_PLUGIN(Mandelbrot) + + +MandelbrotConfig::MandelbrotConfig() +{ +} + +int MandelbrotConfig::equivalent(MandelbrotConfig &that) +{ + return is_julia == that.is_julia && scale == that.scale && + x_off == that.x_off && y_off == that.y_off && + x_julia == that.x_julia && y_julia == that.y_julia && + color == that.color && crunch == that.crunch && + step == that.step; +} + +void MandelbrotConfig::copy_from(MandelbrotConfig &that) +{ + is_julia = that.is_julia; + x_off = that.x_off; + y_off = that.y_off; + scale = that.scale; + x_julia = that.x_julia; + y_julia = that.y_julia; + color = that.color; + crunch = that.crunch; + step = that.step; +} + +void MandelbrotConfig::interpolate( MandelbrotConfig &prev, MandelbrotConfig &next, + long prev_frame, long next_frame, long current_frame) +{ + copy_from(prev); + double u = (double)(next_frame - current_frame) / (next_frame - prev_frame); + double v = 1. - u; + this->x_off = u*prev.x_off + v*next.x_off; + this->y_off = u*prev.y_off + v*next.y_off; + this->scale = u*prev.scale + v*next.scale; + this->x_julia = u*prev.x_julia + v*next.x_julia; + this->y_julia = u*prev.y_julia + v*next.y_julia; +} + +void MandelbrotConfig::limits() +{ + bclamp(scale, -1.e4, 1.e4); + bclamp(crunch, 1, 0x10000); +} + + +Mandelbrot::Mandelbrot(PluginServer *server) + : PluginVClient(server) +{ + config.reset(); + config.startJulia(); + vfrm = 0; + img_w = img_h = 0; + pbo_id = -1; + animation_frame = 0; +} + +Mandelbrot::~Mandelbrot() +{ + delete vfrm; +} + +const char* Mandelbrot::plugin_title() { return N_("Mandelbrot"); } +int Mandelbrot::is_realtime() { return 1; } +int Mandelbrot::is_synthesis() { return 1; } + +NEW_WINDOW_MACRO(Mandelbrot, MandelbrotWindow); +LOAD_CONFIGURATION_MACRO(Mandelbrot, MandelbrotConfig) + +void Mandelbrot::save_data(KeyFrame *keyframe) +{ + FileXML output; + output.set_shared_output(keyframe->xbuf); + output.tag.set_title("MANDELCUDA"); + output.tag.set_property("IS_JULIA", config.is_julia); + output.tag.set_property("SCALE", config.scale); + output.tag.set_property("X_OFF", config.x_off); + output.tag.set_property("Y_OFF", config.y_off); + output.tag.set_property("X_JULIA", config.x_julia); + output.tag.set_property("Y_JULIA", config.y_julia); + output.tag.set_property("COLOR", config.color); + output.tag.set_property("CRUNCH", config.crunch); + output.tag.set_property("STEP", config.step); + output.append_tag(); + output.append_newline(); + output.tag.set_title("/MANDELCUDA"); + output.append_tag(); + output.append_newline(); + output.terminate_string(); +} + +void Mandelbrot::read_data(KeyFrame *keyframe) +{ + FileXML input; + input.set_shared_input(keyframe->xbuf); + + int result = 0; + while( !(result = input.read_tag()) ) { + if( input.tag.title_is("MANDELCUDA") ) { + config.is_julia = input.tag.get_property("IS_JULIA", config.is_julia); + config.scale = input.tag.get_property("SCALE", config.scale); + config.x_off = input.tag.get_property("X_OFF", config.x_off); + config.y_off = input.tag.get_property("Y_OFF", config.y_off); + config.x_julia = input.tag.get_property("X_JULIA", config.x_julia); + config.y_julia = input.tag.get_property("Y_JULIA", config.y_julia); + config.color = input.tag.get_property("COLOR", config.color); + config.crunch = input.tag.get_property("CRUNCH", config.crunch); + config.step = input.tag.get_property("STEP", config.step); + } + } + config.limits(); +} + +void Mandelbrot::update_gui() +{ + if( !thread ) return; + if( !load_configuration() ) return; + thread->window->lock_window("Mandelbrot::update_gui"); + MandelbrotWindow *window = (MandelbrotWindow*)thread->window; + window->update_gui(); + window->flush(); + window->unlock_window(); +} + +void MandelbrotConfig::reset() +{ + is_julia = 0; + x_julia = 0.0; + y_julia = 0.0; + x_off = -0.5; + y_off = 0.0; + scale = 3.2; + color = 0x00030507; + crunch = 512; + step = 0; +} + +void MandelbrotConfig::startJulia() +{ + is_julia = 1; + x_julia = -0.172400; + y_julia = -0.652693; + x_off = -0.085760; + y_off = 0.007040; +} + +// Get a sub-pixel sample location +void Mandelbrot::GetSample(int sampleIndex, float &x, float &y) +{ + static const unsigned char pairData[128][2] = { + {64, 64}, {0, 0}, {1, 63}, {63, 1}, {96, 32}, {97, 95}, {36, 96}, {30, 31}, + {95, 127}, {4, 97}, {33, 62}, {62, 33}, {31, 126}, {67, 99}, {99, 65}, {2, 34}, + {81, 49}, {19, 80}, {113, 17}, {112, 112}, {80, 16}, {115, 81}, {46, 15}, {82, 79}, + {48, 78}, {16, 14}, {49, 113}, {114, 48}, {45, 45}, {18, 47}, {20, 109}, {79, 115}, + {65, 82}, {52, 94}, {15, 124}, {94, 111}, {61, 18}, {47, 30}, {83, 100}, {98, 50}, + {110, 2}, {117, 98}, {50, 59}, {77, 35}, {3, 114}, {5, 77}, {17, 66}, {32, 13}, + {127, 20}, {34, 76}, {35, 110}, {100, 12}, {116, 67}, {66, 46}, {14, 28}, {23, 93}, + {102, 83}, {86, 61}, {44, 125}, {76, 3}, {109, 36}, {6, 51}, {75, 89}, {91, 21}, + {60, 117}, {29, 43}, {119, 29}, {74, 70}, {126, 87}, {93, 75}, {71, 24}, {106, 102}, + {108, 58}, {89, 9}, {103, 23}, {72, 56}, {120, 8}, {88, 40}, {11, 88}, {104, 120}, + {57, 105}, {118, 122}, {53, 6}, {125, 44}, {43, 68}, {58, 73}, {24, 22}, {22, 5}, + {40, 86}, {122, 108}, {87, 90}, {56, 42}, {70, 121}, {8, 7}, {37, 52}, {25, 55}, + {69, 11}, {10, 106}, {12, 38}, {26, 69}, {27, 116}, {38, 25}, {59, 54}, {107, 72}, + {121, 57}, {39, 37}, {73, 107}, {85, 123}, {28, 103}, {123, 74}, {55, 85}, {101, 41}, + {42, 104}, {84, 27}, {111, 91}, {9, 19}, {21, 39}, {90, 53}, {41, 60}, {54, 26}, + {92, 119}, {51, 71}, {124, 101}, {68, 92}, {78, 10}, {13, 118}, {7, 84}, {105, 4} + }; + + x = (1.0f / 128.0f) * (0.5f + (float) pairData[sampleIndex][0]); + y = (1.0f / 128.0f) * (0.5f + (float) pairData[sampleIndex][1]); +} // GetSample + +// render Mandelbrot image using CUDA +void Mandelbrot::renderImage() +{ + float xs, ys; + // Get the anti-alias sub-pixel sample location + GetSample(pass & 127, xs, ys); + + // Get the pixel scale and offset + double s = config.scale / (float) img_w; + double x = (xs - (double) img_w * 0.5f) * s + config.x_off; + double y = (ys - (double) img_h * 0.5f) * s + config.y_off; + + uchar4 colors; + colors.w = (config.color>>24) & 0xff; + colors.x = (config.color>>16) & 0xff; + colors.y = (config.color>>8) & 0xff; + colors.z = (config.color>>0) & 0xff; + + cuda.Run(vfrm->get_data(), img_w*img_h*4, config.is_julia, config.crunch, + x, y, config.x_julia, config.y_julia, s, colors, pass, animation_frame); + ++pass; +} + +void Mandelbrot::displayFunc() +{ + if( config.step ) { + animation_frame += config.step; + pass = 0; + } + // render the Mandelbrot image + renderImage(); +} + +void Mandelbrot::init() +{ + animation_frame = 0; + pass = 0; +} + +int Mandelbrot::process_buffer(VFrame *frame, int64_t start_position, double frame_rate) +{ + + int need_reconfigure = load_configuration(); + if( need_reconfigure ) pass = 0; + output = get_output(0); + color_model = output->get_color_model(); + img_w = output->get_w(); + img_h = output->get_h(); + if( !start_position ) + init(); + if( vfrm && + (vfrm->get_w() != img_w || vfrm->get_h() != img_h) ) { + delete vfrm; vfrm = 0; + } + if( !vfrm ) + vfrm = new VFrame(img_w, img_h, BC_RGBA8888); + + if( get_use_opengl() ) + return run_opengl(); +// always use_opengl + Canvas *canvas = server->mwindow->cwindow->gui->canvas; + return server->mwindow->playback_3d->run_plugin(canvas, this); +} + +// opengl from here down + +void Mandelbrot::init_cuda() +{ + cuda.init_dev(); + GLuint pbo[1]; + glGenBuffers(1, pbo); + glBindBuffer(GL_ARRAY_BUFFER, pbo_id=*pbo); + glBufferData(GL_ARRAY_BUFFER, img_w*img_h*4, 0, GL_STATIC_DRAW); + cuda.init(pbo_id, img_w, img_h); + glBindBuffer(GL_ARRAY_BUFFER, 0); +} +void Mandelbrot::finish_cuda() +{ + cuda.finish(); + GLuint pbo[1]; *pbo = pbo_id; + glDeleteBuffers(1, pbo); + pbo_id = -1; +} + +int Mandelbrot::handle_opengl() +{ + vfrm->enable_opengl(); + vfrm->init_screen(); + init_cuda(); + displayFunc(); + output->transfer_from(vfrm); + finish_cuda(); + return 0; +} + diff --git a/cinelerra-5.1/plugins/mandelcuda/mandelbrot.h b/cinelerra-5.1/plugins/mandelcuda/mandelbrot.h new file mode 100644 index 00000000..c2931cfd --- /dev/null +++ b/cinelerra-5.1/plugins/mandelcuda/mandelbrot.h @@ -0,0 +1,85 @@ +/* + * CINELERRA + * Copyright (C) 1997-2014 Adam Williams + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#ifndef MANDELCUDA_H +#define MANDELCUDA_H + +#include "pluginvclient.h" + +typedef struct { + unsigned char x, y, z, w; +} uchar4; + +#include "mandelcuda.h" + +class MandelbrotConfig; +class Mandelbrot; + +class MandelbrotConfig +{ +public: + MandelbrotConfig(); + + int equivalent(MandelbrotConfig &that); + void copy_from(MandelbrotConfig &that); + void interpolate(MandelbrotConfig &prev, MandelbrotConfig &next, + long prev_frame, long next_frame, long current_frame); + + int is_julia; + float x_off, y_off, scale; + float x_julia, y_julia; + int color, crunch, step; + + void limits(); + void reset(); + void startJulia(); +}; + +class Mandelbrot : public PluginVClient +{ +public: + Mandelbrot(PluginServer *server); + ~Mandelbrot(); + PLUGIN_CLASS_MEMBERS2(MandelbrotConfig) + int is_realtime(); + int is_synthesis(); + void update_gui(); + void save_data(KeyFrame *keyframe); + void read_data(KeyFrame *keyframe); + int process_buffer(VFrame *frame, int64_t start_position, double frame_rate); + int handle_opengl(); + + void GetSample(int sampleIndex, float &x, float &y); + void renderImage(); + void displayFunc(); + void initData(); + void init(); + + VFrame *output, *vfrm; + int color_model, pass; + int img_w, img_h; + int pbo_id; + int animation_frame; + MandelCuda cuda; + + void init_cuda(); + void finish_cuda(); +}; + +#endif diff --git a/cinelerra-5.1/plugins/mandelcuda/mandelbrotwindow.C b/cinelerra-5.1/plugins/mandelcuda/mandelbrotwindow.C new file mode 100644 index 00000000..c4b11687 --- /dev/null +++ b/cinelerra-5.1/plugins/mandelcuda/mandelbrotwindow.C @@ -0,0 +1,215 @@ +/* + * CINELERRA + * Copyright (C) 2014 Adam Williams + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + */ + +#include "bcdisplayinfo.h" +#include "clip.h" +#include "cwindow.h" +#include "cwindowgui.h" +#include "edl.h" +#include "edlsession.h" +#include "language.h" +#include "mandelbrot.h" +#include "mandelbrotwindow.h" +#include "mwindow.h" +#include "mwindowgui.h" +#include "pluginserver.h" +#include "theme.h" + +MandelbrotWindow::MandelbrotWindow(Mandelbrot *plugin) + : PluginClientWindow(plugin, 180, 130, 180, 130, 0) +{ + this->plugin = plugin; + press_x = press_y = 0; + button_no = 0; + pending_config = 0; +} + +MandelbrotWindow::~MandelbrotWindow() +{ +} + +void MandelbrotWindow::create_objects() +{ + int x = 10, y = 10, pad = 5; + BC_Title *title; + add_subwindow(title = new BC_Title(x,y, _("Mandelbrot:"), MEDIUMFONT, YELLOW)); + y += title->get_h() + pad; + add_subwindow(is_julia = new MandelbrotIsJulia(this, x, y)); + y += is_julia->get_h() + pad; + add_subwindow(drag = new MandelbrotDrag(this, x, y)); + y += drag->get_h() + pad; + add_subwindow(reset = new MandelbrotReset(this, x, y)); + show_window(); +} + +void MandelbrotWindow::update_gui() +{ +} + + +void MandelbrotWindow::send_configure_change() +{ + pending_config = 0; + plugin->send_configure_change(); +} + +int MandelbrotWindow::grab_event(XEvent *event) +{ + int ret = do_grab_event(event); + if( pending_config && !grab_event_count() ) + send_configure_change(); + return ret; +} + +int MandelbrotWindow::do_grab_event(XEvent *event) +{ + switch( event->type ) { + case ButtonPress: break; + case ButtonRelease: break; + case MotionNotify: break; + default: + return 0; + } + + MWindow *mwindow = plugin->server->mwindow; + CWindowGUI *cwindow_gui = mwindow->cwindow->gui; + CWindowCanvas *canvas = cwindow_gui->canvas; + int cursor_x, cursor_y; + cwindow_gui->get_relative_cursor(cursor_x, cursor_y); + cursor_x -= canvas->view_x; + cursor_y -= canvas->view_y; + float output_x = cursor_x, output_y = cursor_y; + canvas->canvas_to_output(mwindow->edl, 0, output_x, output_y); + + if( !button_no ) { + if( cursor_x < 0 || cursor_x >= canvas->view_w || + cursor_y < 0 || cursor_y >= canvas->view_h ) + return 0; + } + + switch( event->type ) { + case ButtonPress: + if( button_no ) return 0; + press_x = output_x; press_y = output_y; + button_no = event->xbutton.button; + break; + case ButtonRelease: + if( !button_no ) return 0; + button_no = 0; + return 1; + case MotionNotify: { + if( !button_no ) return 0; + EDL *edl = plugin->get_edl(); + double dx = 0, dy = 0, jx = 0, jy = 0, ds = 1; + double out_w = edl->session->output_w, out_h = edl->session->output_h; + double fx = (double)(press_x - output_x) / (2. * out_w); + double fy = (double)(press_y - output_y) / (2. * out_h); + press_x = output_x; press_y = output_y; + switch( button_no ) { + case LEFT_BUTTON: { + dx = fx * plugin->config.scale; + dy = fy * plugin->config.scale; + break; } + case MIDDLE_BUTTON: { + ds = fy >= 0.f ? 1-fy : 1/(1+fy); + bclamp(ds, 1-0.05f, 1+0.05f); + break; } + case RIGHT_BUTTON: { + jx = fx; + jy = fy; + break; } + } + plugin->config.x_off += dx; + plugin->config.y_off += dy; + plugin->config.x_julia += jx; + plugin->config.y_julia += jy; + plugin->config.scale *= ds; + pending_config = 1; + break; } + default: + return 0; + } + + return 1; +} + +void MandelbrotWindow::done_event(int result) +{ + ungrab(client->server->mwindow->cwindow->gui); +} +MandelbrotDrag::MandelbrotDrag(MandelbrotWindow *gui, int x, int y) + : BC_CheckBox(x, y, 0, _("Drag")) +{ + this->gui = gui; +} +int MandelbrotDrag::handle_event() +{ + CWindowGUI *cwindow_gui = gui->plugin->server->mwindow->cwindow->gui; + int value = get_value(); + if( value ) { + if( !gui->grab(cwindow_gui) ) { + update(value = 0); + flicker(10,50); + } + } + else + gui->ungrab(cwindow_gui); + return 1; +} + +MandelbrotIsJulia::MandelbrotIsJulia(MandelbrotWindow *gui, int x, int y) + : BC_CheckBox(x, y, gui->plugin->config.is_julia, _("Julia")) +{ + this->gui = gui; +} +MandelbrotIsJulia::~MandelbrotIsJulia() +{ +} + +int MandelbrotIsJulia::handle_event() +{ + Mandelbrot *plugin = gui->plugin; + plugin->config.is_julia = get_value(); + gui->send_configure_change(); + return 1; +} + +MandelbrotReset::MandelbrotReset(MandelbrotWindow *gui, int x, int y) + : BC_GenericButton(x, y, _("Reset")) +{ + this->gui = gui; +} +MandelbrotReset::~MandelbrotReset() +{ +} + +int MandelbrotReset::handle_event() +{ + Mandelbrot *plugin = gui->plugin; + int is_julia = plugin->config.is_julia; + plugin->config.reset(); + if( is_julia ) + plugin->config.startJulia(); + gui->send_configure_change(); + return 1; +} + + + diff --git a/cinelerra-5.1/plugins/mandelcuda/mandelbrotwindow.h b/cinelerra-5.1/plugins/mandelcuda/mandelbrotwindow.h new file mode 100644 index 00000000..98208fce --- /dev/null +++ b/cinelerra-5.1/plugins/mandelcuda/mandelbrotwindow.h @@ -0,0 +1,83 @@ +/* + * CINELERRA + * Copyright (C) 2008-2014 Adam Williams + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + */ + +#ifndef MANDELCUDAWINDOW_H +#define MANDELCUDAWINDOW_H + + +#include "guicast.h" +#include "mandelbrot.h" + +class Mandelbrot; +class MandelbrotIsJulia; +class MandelbrotDrag; +class MandelbrotWindow; + +class MandelbrotIsJulia : public BC_CheckBox +{ +public: + MandelbrotIsJulia(MandelbrotWindow *gui, int x, int y); + ~MandelbrotIsJulia(); + int handle_event(); + + MandelbrotWindow *gui; +}; + +class MandelbrotReset : public BC_GenericButton +{ +public: + MandelbrotReset(MandelbrotWindow *gui, int x, int y); + ~MandelbrotReset(); + int handle_event(); + + MandelbrotWindow *gui; +}; + +class MandelbrotDrag : public BC_CheckBox +{ +public: + MandelbrotDrag(MandelbrotWindow *gui, int x, int y); + + int handle_event(); + MandelbrotWindow *gui; +}; + +class MandelbrotWindow : public PluginClientWindow +{ +public: + MandelbrotWindow(Mandelbrot *plugin); + ~MandelbrotWindow(); + void create_objects(); + void update_gui(); + + int grab_event(XEvent *event); + int do_grab_event(XEvent *event); + void done_event(int result); + void send_configure_change(); + + Mandelbrot *plugin; + MandelbrotIsJulia *is_julia; + MandelbrotDrag *drag; + MandelbrotReset *reset; + int press_x, press_y; + int button_no, pending_config; +}; + +#endif diff --git a/cinelerra-5.1/plugins/mandelcuda/mandelcuda.cu b/cinelerra-5.1/plugins/mandelcuda/mandelcuda.cu new file mode 100644 index 00000000..8ba357ea --- /dev/null +++ b/cinelerra-5.1/plugins/mandelcuda/mandelcuda.cu @@ -0,0 +1,160 @@ +#include "mandelcuda.h" +#include +#include +#include "helper_cuda.h" +#include "helper_gl.h" + +// The dimensions of the thread block +#define BLOCKDIM_X 16 +#define BLOCKDIM_Y 16 +#define ABS(n) ((n) < 0 ? -(n) : (n)) + +void MandelCuda::init_dev() +{ + if( numSMs ) return; +// int dev_id = findCudaDevice(argc, (const char **)argv); + int dev_id = gpuGetMaxGflopsDeviceId(); + checkCudaErrors(cudaSetDevice(dev_id)); + cudaDeviceProp deviceProp; + checkCudaErrors(cudaGetDeviceProperties(&deviceProp, dev_id)); +printf("GPU Device %d: \"%s\" with compute capability %d.%d\n", + dev_id, deviceProp.name, deviceProp.major, deviceProp.minor); + version = deviceProp.major * 10 + deviceProp.minor; + numSMs = deviceProp.multiProcessorCount; + if( !numSMs ) numSMs = -1; +} + +void MandelCuda::init(int pbo, int pw, int ph) +{ + if( pbo_id >= 0 ) return; + pbo_id = pbo; pbo_w = pw; pbo_h = ph; + checkCudaErrors(cudaGraphicsGLRegisterBuffer(&cuda_pbo, pbo_id, cudaGraphicsMapFlagsNone)); + checkCudaErrors(cudaGraphicsMapResources(1, &cuda_pbo, 0)); + size_t pbo_bytes = 0; + checkCudaErrors(cudaGraphicsResourceGetMappedPointer(&pbo_mem, &pbo_bytes, cuda_pbo)); +} + +void MandelCuda::finish() +{ + pbo_id = -1; + pbo_w = pbo_h = 0; + checkCudaErrors(cudaGraphicsUnmapResources(1, &cuda_pbo)); + pbo_mem = 0; + cudaGraphicsUnregisterResource(cuda_pbo); cuda_pbo = 0; +} + + +MandelCuda::MandelCuda() +{ + version = 0; + numSMs = 0; + pbo_id = -1; + pbo_w = pbo_h = 0; + cuda_pbo = 0; + pbo_mem = 0; +} +MandelCuda::~MandelCuda() +{ +} + +static inline int iDivUp(int a, int b) +{ + int v = a / b; + return a % b ? v+1 : v; +} + +// Determine if two pixel colors are within tolerance +__device__ inline int CheckColors(const uchar4 &color0, const uchar4 &color1) +{ + int x = color1.x - color0.x; + if( ABS(x) > 10 ) return 1; + int y = color1.y - color0.y; + if( ABS(y) > 10 ) return 1; + int z = color1.z - color0.z; + if( ABS(z) > 10 ) return 1; + return 0; +} + + +// The core MandelCuda calculation function template +template __device__ +inline int CalcCore(const int n, T ix, T iy, T xC, T yC) +{ + T x = ix, y = iy; + T xx = x * x, yy = y * y; + int i = n; + while( --i && (xx + yy < 4.0f) ) { + y = x * y + x * y + yC ; // 2*x*y + yC + x = xx - yy + xC ; + yy = y * y; + xx = x * x; + } + + return i; +} + +template __global__ +void Calc(uchar4 *dst, const int img_w, const int img_h, const int is_julia, + const int crunch, const int gridWidth, const int numBlocks, + const T x_off, const T y_off, const T x_julia, const T y_julia, const T scale, + const uchar4 colors, const int frame, const int animationFrame) +{ + // loop until all blocks completed + for( unsigned int bidx=blockIdx.x; bidx= img_w || y >= img_h ) continue; + int pi = img_w*y + x, n = !frame ? 1 : 0; + uchar4 pixel = dst[pi]; + if( !n && x > 0 ) + n += CheckColors(pixel, dst[pi-1]); + if( !n && x+1 < img_w ) + n += CheckColors(pixel, dst[pi+1]); + if( !n && y > 0 ) + n += CheckColors(pixel, dst[pi-img_w]); + if( !n && y+1 < img_h ) + n += CheckColors(pixel, dst[pi+img_w]); + if( !n ) continue; + + const T tx = T(x) * scale + x_off; + const T ty = T(y) * scale + y_off; + const T ix = is_julia ? tx : 0; + const T iy = is_julia ? ty : 0; + const T xC = is_julia ? x_julia : tx; + const T yC = is_julia ? y_julia : ty; + int m = CalcCore(crunch, ix,iy, xC,yC); + m = m > 0 ? crunch - m : 0; + if( m ) m += animationFrame; + + uchar4 color; + color.x = m * colors.x; + color.y = m * colors.y; + color.z = m * colors.z; + color.w = 0; + + int frame1 = frame+1, frame2 = frame1/2; + color.x = (pixel.x * frame + color.x + frame2) / frame1; + color.y = (pixel.y * frame + color.y + frame2) / frame1; + color.z = (pixel.z * frame + color.z + frame2) / frame1; + dst[pi] = color; // Output the pixel + } +} + + +void MandelCuda::Run(unsigned char *data, unsigned int size, int is_julia, int crunch, + double x_off, double y_off, double x_julia, double y_julia, double scale, + uchar4 colors, int pass, int animationFrame) +{ + if( numSMs < 0 ) return; + checkCudaErrors(cudaMemcpy(pbo_mem, data, size, cudaMemcpyHostToDevice)); + dim3 threads(BLOCKDIM_X, BLOCKDIM_Y); + dim3 grid(iDivUp(pbo_w, BLOCKDIM_X), iDivUp(pbo_h, BLOCKDIM_Y)); + Calc<<>>((uchar4 *)pbo_mem, pbo_w, pbo_h, + is_julia, crunch, grid.x, grid.x*grid.y, + float(x_off), float(y_off), float(x_julia), float(y_julia), float(scale), + colors, pass, animationFrame); + checkCudaErrors(cudaMemcpy(data, pbo_mem, size, cudaMemcpyDeviceToHost)); +} + diff --git a/cinelerra-5.1/plugins/mandelcuda/mandelcuda.h b/cinelerra-5.1/plugins/mandelcuda/mandelcuda.h new file mode 100644 index 00000000..3fc9c48f --- /dev/null +++ b/cinelerra-5.1/plugins/mandelcuda/mandelcuda.h @@ -0,0 +1,23 @@ +#ifndef __MANDELCUDA_CUH__ +#define __MANDELCUDA_CUH__ + +class MandelCuda +{ +public: + MandelCuda(); + ~MandelCuda(); + + void init_dev(); + void Run(unsigned char *data, unsigned int size, int is_julia, int crunch, + double x, double y, double jx, double jy, double scale, + uchar4 color, int pass, int animationFrame); + void init(int pbo, int pw, int ph); + void finish(); + + int version, numSMs; + int pbo_id, pbo_w, pbo_h; + struct cudaGraphicsResource *cuda_pbo; + void *pbo_mem; +}; + +#endif diff --git a/cinelerra-5.1/plugins/nbodycuda/.swp b/cinelerra-5.1/plugins/nbodycuda/.swp new file mode 100644 index 00000000..5d9b1b9c Binary files /dev/null and b/cinelerra-5.1/plugins/nbodycuda/.swp differ diff --git a/cinelerra-5.1/plugins/nbodycuda/Makefile b/cinelerra-5.1/plugins/nbodycuda/Makefile new file mode 100644 index 00000000..a99f748f --- /dev/null +++ b/cinelerra-5.1/plugins/nbodycuda/Makefile @@ -0,0 +1,20 @@ +TOPDIR?=../.. +include $(TOPDIR)/plugin_defs +include $(TOPDIR)/plugin_cuda + +PLUGIN = nbodycuda + +OBJS := \ + $(OBJDIR)/nbody.o \ + $(OBJDIR)/nbodywindow.o \ + $(OBJDIR)/nbodycuda.o \ + $(OBJDIR)/bodysys.o \ + $(OBJDIR)/renders.o \ + +include $(TOPDIR)/plugin_config + +$(OBJDIR)/nbody.o: nbody.C nbody.h +$(OBJDIR)/nbodywindow.o: nbodywindow.C nbodywindow.h +$(OBJDIR)/nbodycuda.o: nbodycuda.cu nbodycuda.h +$(OBJDIR)/bodysys.o: bodysys.cu +$(OBJDIR)/renders.o: renders.C diff --git a/cinelerra-5.1/plugins/nbodycuda/bodysys.cu b/cinelerra-5.1/plugins/nbodycuda/bodysys.cu new file mode 100644 index 00000000..76c997be --- /dev/null +++ b/cinelerra-5.1/plugins/nbodycuda/bodysys.cu @@ -0,0 +1 @@ +#include "5_Simulations/nbody/bodysystemcuda.cu" diff --git a/cinelerra-5.1/plugins/nbodycuda/nbody.C b/cinelerra-5.1/plugins/nbodycuda/nbody.C new file mode 100644 index 00000000..ae15e643 --- /dev/null +++ b/cinelerra-5.1/plugins/nbodycuda/nbody.C @@ -0,0 +1,392 @@ +/* + * CINELERRA + * Copyright (C) 1997-2014 Adam Williams + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + */ + +#define GL_GLEXT_PROTOTYPES +#include +#include +#include + +#include "clip.h" +#include "filexml.h" +#include "language.h" +#include "mutex.h" + +#include "cwindow.h" +#include "cwindowgui.h" +#include "mwindow.h" +#include "pluginserver.h" +#include "playback3d.h" + +#include "nbody.h" +#include "nbodycuda.h" +#include "nbodywindow.h" + + +static struct N_BodyParams demoParams[] = { + { 0.016f, 1.54f, 8.0f, 0.1f, 1.0f, 1.0f, 0, -2, -100}, + { 0.016f, 0.68f, 20.0f, 0.1f, 1.0f, 0.8f, 0, -2, -30}, + { 0.0006f, 0.16f, 1000.0f, 1.0f, 1.0f, 0.07f, 0, 0, -1.5f}, + { 0.0006f, 0.16f, 1000.0f, 1.0f, 1.0f, 0.07f, 0, 0, -1.5f}, + { 0.0019f, 0.32f, 276.0f, 1.0f, 1.0f, 0.07f, 0, 0, -5}, + { 0.0016f, 0.32f, 272.0f, 0.145f, 1.0f, 0.08f, 0, 0, -5}, + { 0.0160f, 6.04f, 0.0f, 1.0f, 1.0f, 0.76f, 0, 0, -50}, +}; +const int N_BodyParams::num_demos = sizeof(demoParams)/sizeof(*demoParams); + + +REGISTER_PLUGIN(N_BodyMain) + +void N_BodyConfig::reset(int i) +{ + *(N_BodyParams*)this = demoParams[i]; + trans[0] = trans_lag[0] = m_x; + trans[1] = trans_lag[1] = m_y; + trans[2] = trans_lag[2] = m_z; + rot[0] = rot_lag[0] = 0; + rot[1] = rot_lag[1] = 0; + rot[2] = rot_lag[2] = 0; + mode = ParticleRenderer::PARTICLE_SPRITES_COLOR; + numBodies = 4096; + inertia = 0.1; +} + +N_BodyConfig::N_BodyConfig() +{ + reset(); +} + +int N_BodyConfig::equivalent(N_BodyConfig &that) +{ + return m_timestep == that.m_timestep && + m_clusterScale == that.m_clusterScale && + m_velocityScale == that.m_velocityScale && + m_softening == that. m_softening && + m_damping == that.m_damping && + m_pointSize == that.m_pointSize && + m_x == that.m_x && + m_y == that.m_y && + m_z == that.m_z && + trans[0] == that.trans[0] && + trans[1] == that.trans[1] && + trans[2] == that.trans[2] && + trans_lag[0] == that.trans_lag[0] && + trans_lag[1] == that.trans_lag[1] && + trans_lag[2] == that.trans_lag[2] && + rot[0] == that.rot[0] && + rot[1] == that.rot[1] && + rot[2] == that.rot[2] && + rot_lag[0] == that.rot_lag[0] && + rot_lag[1] == that.rot_lag[1] && + rot_lag[2] == that.rot_lag[2] && + inertia == that.inertia && + numBodies == that.numBodies; + return 1; +} + +void N_BodyConfig::copy_from(N_BodyConfig &that) +{ + m_timestep = that.m_timestep; + m_clusterScale = that.m_clusterScale; + m_velocityScale = that.m_velocityScale; + m_softening = that. m_softening; + m_damping = that.m_damping; + m_pointSize = that.m_pointSize; + m_x = that.m_x; + m_y = that.m_y; + m_z = that.m_z; + trans[0] = that.trans[0]; + trans[1] = that.trans[1]; + trans[2] = that.trans[2]; + trans_lag[0] = that.trans_lag[0]; + trans_lag[1] = that.trans_lag[1]; + trans_lag[2] = that.trans_lag[2]; + rot[0] = that.rot[0]; + rot[1] = that.rot[1]; + rot[2] = that.rot[2]; + rot_lag[0] = that.rot_lag[0]; + rot_lag[1] = that.rot_lag[1]; + rot_lag[2] = that.rot_lag[2]; + inertia = that.inertia; + numBodies = that.numBodies; +} + +void N_BodyConfig::interpolate( N_BodyConfig &prev, N_BodyConfig &next, + long prev_frame, long next_frame, long current_frame) +{ + copy_from(next); +} + +void N_BodyConfig::limits() +{ + if( m_damping < 0.001 ) m_damping = 0.001; + if( trans[2] < 0.005 ) trans[2] = 0.005; + int n = 1; + while( n < numBodies ) n <<= 1; + bclamp(n, 0x0010, 0x4000); + numBodies = n; + bclamp(inertia, 0.f,1.f); + bclamp(mode, 0, (int)ParticleRenderer::PARTICLE_NUM_MODES-1); +} + + +N_BodyMain::N_BodyMain(PluginServer *server) + : PluginVClient(server) +{ + cuda = 0; + blockSize = 256; + + m_nbody = 0; + m_renderer = 0; + m_hPos = 0; + m_hVel = 0; + m_hColor = 0; + + curr_position = -1; + new_position = -1; +} + +N_BodyMain::~N_BodyMain() +{ + delete cuda; +} + +void N_BodyMain::init(int numBodies) +{ + selectDemo(0); + delete m_nbody; m_nbody = new N_BodySystem(numBodies, 1, blockSize); + int sz = numBodies*4; + delete [] m_hPos; m_hPos = new float[sz]; + delete [] m_hVel; m_hVel = new float[sz]; + delete [] m_hColor; m_hColor = new float[sz]; + delete m_renderer; m_renderer = new ParticleRenderer; +// config here + m_nbody->setSoftening(config.m_softening); + m_nbody->setDamping(config.m_damping); + reset(numBodies, NBODY_CONFIG_RANDOM); + resetRenderer(); +} + +void N_BodyMain::reset(int numBodies, NBodyConfig cfg) +{ + randomizeBodies(cfg, m_hPos, m_hVel, m_hColor, + config.m_clusterScale, config.m_velocityScale, + numBodies, true); + setArrays(m_hPos, m_hVel); +} + +void N_BodyMain::resetRenderer() +{ + float color[4] = { 1.0f, 0.6f, 0.3f, 1.0f}; + m_renderer->setBaseColor(color); + m_renderer->setColors(m_hColor, m_nbody->getNumBodies()); + m_renderer->setSpriteSize(config.m_pointSize); +} + +void N_BodyMain::selectDemo(int index) +{ + config.reset(index); +} + +void N_BodyMain::finalize() +{ + delete [] m_hPos; m_hPos = 0; + delete [] m_hVel; m_hVel = 0; + delete [] m_hColor; m_hColor = 0; + delete m_nbody; m_nbody = 0; + delete m_renderer; m_renderer = 0; +} + +void N_BodyMain::draw() +{ + cuda->draw_event(); + glClearColor(0.,0.,0.,1.); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + glColor4f(1.,1.,1.,1.); + glMatrixMode(GL_MODELVIEW); + glLoadIdentity(); + float inertia = config.inertia; + for( int c=0; c<3; ++c ) { + config.trans_lag[c] += (config.trans[c] - config.trans_lag[c]) * inertia; + config.rot_lag[c] += (config.rot[c] - config.rot_lag[c]) * inertia; + } + + glTranslatef(config.trans_lag[0], config.trans_lag[1], config.trans_lag[2]); + glRotatef(config.rot_lag[0], 1.0, 0.0, 0.0); + glRotatef(config.rot_lag[1], 0.0, 1.0, 0.0); + glDisable(GL_TEXTURE_2D); + display(); +} + + +const char* N_BodyMain::plugin_title() { return N_("N_Body"); } +int N_BodyMain::is_realtime() { return 1; } +int N_BodyMain::is_synthesis() { return 1; } + +NEW_WINDOW_MACRO(N_BodyMain, N_BodyWindow); +LOAD_CONFIGURATION_MACRO(N_BodyMain, N_BodyConfig) + +void N_BodyMain::save_data(KeyFrame *keyframe) +{ + FileXML output; + +// cause data to be stored directly in text + output.set_shared_output(keyframe->xbuf); + output.tag.set_title("NBODYCUDA"); + output.tag.set_property("TIMESTEP", config.m_timestep); + output.tag.set_property("CLUSTER_SCALE", config.m_clusterScale); + output.tag.set_property("VELOCITY_SCALE", config.m_velocityScale); + output.tag.set_property("SOFTENING", config.m_softening); + output.tag.set_property("DAMPING", config.m_damping); + output.tag.set_property("POINT_SIZE", config.m_pointSize); + output.tag.set_property("X", config.m_x); + output.tag.set_property("Y", config.m_y); + output.tag.set_property("Z", config.m_z); + output.tag.set_property("TRANS_X",config.trans[0]); + output.tag.set_property("TRANS_Y",config.trans[1]); + output.tag.set_property("TRANS_Z",config.trans[2]); + output.tag.set_property("TRANS_LAG_X",config.trans_lag[0]); + output.tag.set_property("TRANS_LAG_Y",config.trans_lag[1]); + output.tag.set_property("TRANS_LAG_Z",config.trans_lag[2]); + output.tag.set_property("ROT_X",config.rot[0]); + output.tag.set_property("ROT_Y",config.rot[1]); + output.tag.set_property("ROT_Z",config.rot[2]); + output.tag.set_property("ROT_LAG_X",config.rot_lag[0]); + output.tag.set_property("ROT_LAG_Y",config.rot_lag[1]); + output.tag.set_property("ROT_LAG_Z",config.rot_lag[2]); + output.tag.set_property("INERTIA", config.inertia); + output.tag.set_property("MODE", config.mode); + output.tag.set_property("NUM_BODIES", config.numBodies); + output.append_tag(); + output.append_newline(); + output.tag.set_title("/NBODYCUDA"); + output.append_tag(); + output.append_newline(); + output.terminate_string(); +} + +void N_BodyMain::read_data(KeyFrame *keyframe) +{ + FileXML input; + input.set_shared_input(keyframe->xbuf); + + int result = 0; + while( !(result = input.read_tag()) ) { + if( input.tag.title_is("NBODYCUDA") ) { + config.m_timestep = input.tag.get_property("TIMESTEP", config.m_timestep); + config.m_clusterScale = input.tag.get_property("CLUSTER_SCALE", config.m_clusterScale); + config.m_velocityScale = input.tag.get_property("VELOCITY_SCALE", config.m_velocityScale); + config.m_softening = input.tag.get_property("SOFTENING", config.m_softening); + config.m_damping = input.tag.get_property("DAMPING", config.m_damping); + config.m_pointSize = input.tag.get_property("POINT_SIZE", config.m_pointSize); + config.m_x = input.tag.get_property("X", config.m_x); + config.m_y = input.tag.get_property("Y", config.m_y); + config.m_z = input.tag.get_property("Z", config.m_z); + config.trans[0] = input.tag.get_property("TRANS_X", config.trans[0]); + config.trans[1] = input.tag.get_property("TRANS_Y", config.trans[1]); + config.trans[2] = input.tag.get_property("TRANS_Z", config.trans[2]); + config.trans_lag[0] = input.tag.get_property("TRANS_LAG_X", config.trans_lag[0]); + config.trans_lag[1] = input.tag.get_property("TRANS_LAG_Y", config.trans_lag[1]); + config.trans_lag[2] = input.tag.get_property("TRANS_LAG_Z", config.trans_lag[2]); + config.rot[0] = input.tag.get_property("ROT_X", config.rot[0]); + config.rot[1] = input.tag.get_property("ROT_Y", config.rot[1]); + config.rot[2] = input.tag.get_property("ROT_Z", config.rot[2]); + config.rot_lag[0] = input.tag.get_property("ROT_LAG_X", config.rot_lag[0]); + config.rot_lag[1] = input.tag.get_property("ROT_LAG_Y", config.rot_lag[1]); + config.rot_lag[2] = input.tag.get_property("ROT_LAG_Z", config.rot_lag[2]); + config.inertia = input.tag.get_property("INERTIA", config.inertia); + config.mode = input.tag.get_property("MODE", config.mode); + config.numBodies = input.tag.get_property("NUM_BODIES", config.numBodies); + } + } + config.limits(); +} + +void N_BodyMain::update_gui() +{ + if( !thread ) return; + if( !load_configuration() ) return; + thread->window->lock_window("N_BodyMain::update_gui"); + N_BodyWindow *window = (N_BodyWindow*)thread->window; + window->update_gui(); + window->flush(); + window->unlock_window(); +} + +int N_BodyMain::process_buffer(VFrame *frame, int64_t start_position, double frame_rate) +{ + + //int need_reconfigure = + load_configuration(); + new_position = start_position; + output = get_output(0); + color_model = output->get_color_model(); + if( get_use_opengl() ) + return run_opengl(); +// always use_opengl + Canvas *canvas = server->mwindow->cwindow->gui->canvas; + return server->mwindow->playback_3d->run_plugin(canvas, this); +} + +// cuda + +N_BodyCuda::N_BodyCuda() +{ + version = 0; + numSMs = 0; +} +N_BodyCuda::~N_BodyCuda() +{ +} + +// opengl from here down + +void N_BodyMain::init_cuda() +{ + if( !cuda ) { + cuda = new N_BodyCuda(); + cuda->init_dev(); + } + cuda->init(); +} +void N_BodyMain::finish_cuda() +{ + cuda->finish(); +} + +int N_BodyMain::handle_opengl() +{ + output->enable_opengl(); + output->init_screen(); + if( !m_nbody || get_source_position() == 0 || + (int)m_nbody->getNumBodies() != config.numBodies ) + init(config.numBodies); + init_cuda(); + if( curr_position != new_position ) { + updateSimulation(); + curr_position = new_position; + } + draw(); + finish_cuda(); + output->set_opengl_state(VFrame::SCREEN); + if( !get_use_opengl() ) // rendering + output->screen_to_ram(); + return 0; +} + diff --git a/cinelerra-5.1/plugins/nbodycuda/nbody.h b/cinelerra-5.1/plugins/nbodycuda/nbody.h new file mode 100644 index 00000000..3d97e6a1 --- /dev/null +++ b/cinelerra-5.1/plugins/nbodycuda/nbody.h @@ -0,0 +1,150 @@ +/* + * CINELERRA + * Copyright (C) 1997-2014 Adam Williams + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#ifndef NBODYCUDA_H +#define NBODYCUDA_H + +#include "pluginvclient.h" + +#include +#include +#include +#include + +#include <5_Simulations/nbody/bodysystemcuda.h> +#include <5_Simulations/nbody/render_particles.h> +#include "nbodycuda.h" + +class N_BodyConfig; +class N_BodyMain; +class N_BodyCuda; + + +class N_BodyParams +{ +public: + float m_timestep, m_clusterScale, m_velocityScale; + float m_softening, m_damping, m_pointSize; + float m_x, m_y, m_z; + static const int num_demos; +}; +class N_BodyCamera +{ +public: + float trans[3]; + float rot[3]; + float trans_lag[3]; + float rot_lag[3]; +}; + +class N_BodyConfig : public N_BodyParams, public N_BodyCamera +{ +public: + N_BodyConfig(); + void reset(int i=0); + int mode; + float inertia; + int numBodies; + + int equivalent(N_BodyConfig &that); + void copy_from(N_BodyConfig &that); + void interpolate(N_BodyConfig &prev, N_BodyConfig &next, + long prev_frame, long next_frame, long current_frame); + void limits(); +}; + +class N_BodyMain : public PluginVClient +{ +public: + N_BodyMain(PluginServer *server); + ~N_BodyMain(); + PLUGIN_CLASS_MEMBERS2(N_BodyConfig) + int is_realtime(); + int is_synthesis(); + void update_gui(); + void save_data(KeyFrame *keyframe); + void read_data(KeyFrame *keyframe); + int process_buffer(VFrame *frame, int64_t start_position, double frame_rate); + void initData(); + void reset(); + int handle_opengl(); + + int color_model, pass; + VFrame *output; + N_BodyCuda *cuda; + + void init_cuda(); + void finish_cuda(); + + BodySystem *m_nbody; + ParticleRenderer *m_renderer; + + float *m_hPos, *m_hVel; + float *m_hColor; + + char deviceName[100]; + enum { M_VIEW = 0, M_MOVE }; + int blockSize; + + int activeDemo; + int64_t curr_position, new_position; + + void init(int numBodies); + void reset(int numBodies, NBodyConfig cfg); + void resetRenderer(); + void selectDemo(int index); + void updateParams() { + m_nbody->setSoftening(config.m_softening); + m_nbody->setDamping(config.m_damping); + } + + void updateSimulation() { + m_nbody->update(config.m_timestep); + } + + void display() { // display particles + m_renderer->setSpriteSize(config.m_pointSize); + m_renderer->setPBO(m_nbody->getCurrentReadBuffer(), + m_nbody->getNumBodies(), (sizeof(float) > 4)); + m_renderer->display((ParticleRenderer::DisplayMode)config.mode); + } + void draw(); + + void getArrays(float *pos, float *vel) { + float *_pos = m_nbody->getArray(BODYSYSTEM_POSITION); + float *_vel = m_nbody->getArray(BODYSYSTEM_VELOCITY); + memcpy(pos, _pos, m_nbody->getNumBodies() * 4 * sizeof(float)); + memcpy(vel, _vel, m_nbody->getNumBodies() * 4 * sizeof(float)); + } + + void setArrays(const float *pos, const float *vel) { + int sz = config.numBodies * 4 * sizeof(float); + if (pos != m_hPos) + memcpy(m_hPos, pos, sz); + if (vel != m_hVel) + memcpy(m_hVel, vel, sz); + m_nbody->setArray(BODYSYSTEM_POSITION, m_hPos); + m_nbody->setArray(BODYSYSTEM_VELOCITY, m_hVel); + resetRenderer(); + } + + void finalize(); +}; + +#endif diff --git a/cinelerra-5.1/plugins/nbodycuda/nbodycuda.cu b/cinelerra-5.1/plugins/nbodycuda/nbodycuda.cu new file mode 100644 index 00000000..b82c79fd --- /dev/null +++ b/cinelerra-5.1/plugins/nbodycuda/nbodycuda.cu @@ -0,0 +1,35 @@ +#include +#include +#include "helper_cuda.h" +#include "helper_gl.h" + +#include "nbodycuda.h" + +void N_BodyCuda::init() +{ + checkCudaErrors(cudaEventCreate(&startEvent)); + checkCudaErrors(cudaEventCreate(&stopEvent)); + checkCudaErrors(cudaEventCreate(&hostMemSyncEvent)); +} + +void N_BodyCuda::init_dev() +{ +// int dev_id = findCudaDevice(argc, (const char **)argv); + int dev_id = gpuGetMaxGflopsDeviceId(); + checkCudaErrors(cudaSetDevice(dev_id)); + cudaDeviceProp deviceProp; + checkCudaErrors(cudaGetDeviceProperties(&deviceProp, dev_id)); +printf("GPU Device %d: \"%s\" with compute capability %d.%d\n", + dev_id, deviceProp.name, deviceProp.major, deviceProp.minor); + version = deviceProp.major * 10 + deviceProp.minor; + numSMs = deviceProp.multiProcessorCount; +} + + +void N_BodyCuda::finish() +{ + checkCudaErrors(cudaEventDestroy(startEvent)); + checkCudaErrors(cudaEventDestroy(stopEvent)); + checkCudaErrors(cudaEventDestroy(hostMemSyncEvent)); +} + diff --git a/cinelerra-5.1/plugins/nbodycuda/nbodycuda.h b/cinelerra-5.1/plugins/nbodycuda/nbodycuda.h new file mode 100644 index 00000000..b1a9cb05 --- /dev/null +++ b/cinelerra-5.1/plugins/nbodycuda/nbodycuda.h @@ -0,0 +1,41 @@ +#ifndef __NBODYCUDA_H__ +#define __NBODYCUDA_H__ + +#include +template +void read_tipsy_file(std::vector &bodyPositions, std::vector &bodyVelocities, + std::vector &bodiesIDs, const std::string &fileName, + int &NTotal, int &NFirst, int &NSecond, int &NThird) +{ +} + +#include <5_Simulations/nbody/bodysystem.h> +#include <5_Simulations/nbody/bodysystemcuda.h> + +class N_BodyCuda +{ +public: + N_BodyCuda(); + ~N_BodyCuda(); + void init_dev(); + void init(); + void finish(); + + int version, numSMs; + + cudaEvent_t startEvent, stopEvent, hostMemSyncEvent; + void start_event() { cudaEventRecord(startEvent, 0); } + void stop_event() { cudaEventRecord(stopEvent, 0); } + void draw_event() { cudaEventRecord(hostMemSyncEvent, 0); } +}; + +class N_BodySystem : public BodySystemCUDA +{ +public: + N_BodySystem(int n_bodies, int n_devs, int blockSize) + : BodySystemCUDA(n_bodies, n_devs, blockSize, 1) {} + N_BodySystem() {}; + virtual void loadTipsyFile(const std::string &filename) {} +}; + +#endif diff --git a/cinelerra-5.1/plugins/nbodycuda/nbodywindow.C b/cinelerra-5.1/plugins/nbodycuda/nbodywindow.C new file mode 100644 index 00000000..c5c7766e --- /dev/null +++ b/cinelerra-5.1/plugins/nbodycuda/nbodywindow.C @@ -0,0 +1,286 @@ +/* + * CINELERRA + * Copyright (C) 2014 Adam Williams + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + */ + +#include "bcdisplayinfo.h" +#include "clip.h" +#include "cwindow.h" +#include "cwindowgui.h" +#include "language.h" +#include "nbody.h" +#include "nbodywindow.h" +#include "mwindow.h" +#include "mwindowgui.h" +#include "pluginserver.h" +#include "theme.h" + +static const char *display_modes[] = { + N_("point"), + N_("sprite"), + N_("color"), +}; +static const int num_display_modes = sizeof(display_modes)/sizeof(*display_modes); + +N_BodyWindow::N_BodyWindow(N_BodyMain *plugin) + : PluginClientWindow(plugin, 240, 200, 240, 200, 0) +{ + this->plugin = plugin; + press_x = press_y = 0; + button_no = 0; + pending_config = 0; +} + +N_BodyWindow::~N_BodyWindow() +{ +} + +void N_BodyWindow::create_objects() +{ + int x = 10, y = 10, pad = 5; + int x1 = 100; + BC_Title *title; + add_subwindow(title = new BC_Title(x,y, _("NBody"), MEDIUMFONT, YELLOW)); + y += title->get_h() + 2*pad; + add_subwindow(title = new BC_Title(x,y, _("set demo:"))); + set_demo = new N_BodySetDemo(this, x1,y, "0"); + set_demo->create_objects(); + y += set_demo->get_h() + pad; + add_subwindow(title = new BC_Title(x,y, _("draw mode:"))); + set_mode = new N_BodySetMode(this, x1,y, _(display_modes[plugin->config.mode])); + set_mode->create_objects(); + y += set_mode->get_h() + pad; + add_subwindow(title = new BC_Title(x,y, _("numBodies:"))); + char text[BCSTRLEN]; + sprintf(text, "%d", plugin->config.numBodies); + num_bodies = new N_BodyNumBodies(this, x1,y, text); + num_bodies->create_objects(); + y += num_bodies->get_h() + pad; + add_subwindow(drag = new N_BodyDrag(this, x, y)); + y += drag->get_h() + pad; + add_subwindow(reset = new N_BodyReset(this, x, y)); + show_window(); +} + +void N_BodyWindow::update_gui() +{ + set_mode->update(_(display_modes[plugin->config.mode])); + char text[BCSTRLEN]; + sprintf(text, "%d", plugin->config.numBodies); + num_bodies->update(text); +} + + +void N_BodyWindow::send_configure_change() +{ + pending_config = 0; + plugin->send_configure_change(); +} + +int N_BodyWindow::grab_event(XEvent *event) +{ + int ret = do_grab_event(event); + if( pending_config && !grab_event_count() ) + send_configure_change(); + return ret; +} + +int N_BodyWindow::do_grab_event(XEvent *event) +{ + switch( event->type ) { + case ButtonPress: break; + case ButtonRelease: break; + case MotionNotify: break; + default: + return 0; + } + + MWindow *mwindow = plugin->server->mwindow; + CWindowGUI *cwindow_gui = mwindow->cwindow->gui; + CWindowCanvas *canvas = cwindow_gui->canvas; + int cursor_x, cursor_y; + cwindow_gui->get_relative_cursor(cursor_x, cursor_y); + cursor_x -= canvas->view_x; + cursor_y -= canvas->view_y; + float output_x = cursor_x, output_y = cursor_y; + canvas->canvas_to_output(mwindow->edl, 0, output_x, output_y); + + if( !button_no ) { + if( cursor_x < 0 || cursor_x >= canvas->view_w || + cursor_y < 0 || cursor_y >= canvas->view_h ) + return 0; + } + + switch( event->type ) { + case ButtonPress: + if( button_no ) return 0; + press_x = output_x; press_y = output_y; + button_no = event->xbutton.button; + break; + case ButtonRelease: + if( !button_no ) return 0; + button_no = 0; + return 1; + case MotionNotify: { + if( !button_no ) return 0; + N_BodyConfig &config = plugin->config; + double dx = (double)(press_x - output_x); + double dy = (double)(press_y - output_y); + press_x = output_x; press_y = output_y; + switch( button_no ) { + case LEFT_BUTTON: { + config.trans[0] += dx / 5.0f; + config.trans[1] -= dy / 5.0f; + break; } + case MIDDLE_BUTTON: { + double s = 0.5f * fabs(config.trans[2]); + if( s < 0.1 ) s = 0.1; + config.trans[2] += (dy / 100.0f) * s; + break; } + case RIGHT_BUTTON: { + config.rot[0] += dy / 5.0f; + config.rot[1] += dx / 5.0f; + break; } + } + pending_config = 1; + break; } + default: + return 0; + } + + return 1; +} + +void N_BodyWindow::done_event(int result) +{ + ungrab(client->server->mwindow->cwindow->gui); +} + +N_BodyDrag::N_BodyDrag(N_BodyWindow *gui, int x, int y) + : BC_CheckBox(x, y, 0, _("Drag")) +{ + this->gui = gui; +} +int N_BodyDrag::handle_event() +{ + CWindowGUI *cwindow_gui = gui->plugin->server->mwindow->cwindow->gui; + int value = get_value(); + if( value ) { + if( !gui->grab(cwindow_gui) ) { + update(value = 0); + flicker(10,50); + } + } + else + gui->ungrab(cwindow_gui); + return 1; +} + +N_BodySetMode::N_BodySetMode(N_BodyWindow *gui, int x, int y, const char *text) + : BC_PopupTextBox(gui, 0, text, x, y, 100, 160) +{ + this->gui = gui; +} + +void N_BodySetMode::create_objects() +{ + BC_PopupTextBox::create_objects(); + for( int i=0; iplugin; + plugin->config.mode = get_number(); + plugin->send_configure_change(); + return 1; +} + + +N_BodySetDemo::N_BodySetDemo(N_BodyWindow *gui, int x, int y, const char *text) + : BC_PopupTextBox(gui, 0, text, x, y, 100, 160) +{ + this->gui = gui; +} + +void N_BodySetDemo::create_objects() +{ + BC_PopupTextBox::create_objects(); + for( int i=0; iplugin; + plugin->selectDemo(get_number()); + gui->update_gui(); + plugin->send_configure_change(); + return 1; +} + +N_BodyNumBodies::N_BodyNumBodies(N_BodyWindow *gui, int x, int y, const char *text) + : BC_PopupTextBox(gui, 0, text, x, y, 100, 160) +{ + this->gui = gui; +} + +void N_BodyNumBodies::create_objects() +{ + BC_PopupTextBox::create_objects(); + for( int i=0; i<8; ++i ) { + char text[BCSTRLEN]; sprintf(text,"%d",1<<(i+6)); + num_body_items.append(new BC_ListBoxItem(text)); + } + update_list(&num_body_items); +} + +int N_BodyNumBodies::handle_event() +{ + N_BodyMain *plugin = gui->plugin; + int i = get_number(); + int n = i >= 0 ? (1 << (i+6)) : atoi(get_text()); + bclamp(n, 0x10,0x4000); + plugin->config.numBodies = n; + plugin->send_configure_change(); + return 1; +} + +N_BodyReset::N_BodyReset(N_BodyWindow *gui, int x, int y) + : BC_GenericButton(x, y, _("Reset")) +{ + this->gui = gui; +} +N_BodyReset::~N_BodyReset() +{ +} + +int N_BodyReset::handle_event() +{ + N_BodyMain *plugin = gui->plugin; + plugin->config.reset(); + gui->update_gui(); + gui->send_configure_change(); + return 1; +} + diff --git a/cinelerra-5.1/plugins/nbodycuda/nbodywindow.h b/cinelerra-5.1/plugins/nbodycuda/nbodywindow.h new file mode 100644 index 00000000..b4b04c0b --- /dev/null +++ b/cinelerra-5.1/plugins/nbodycuda/nbodywindow.h @@ -0,0 +1,137 @@ +/* + * CINELERRA + * Copyright (C) 2008-2014 Adam Williams + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + * + */ + +#ifndef NBODYCUDAWINDOW_H +#define NBODYCUDAWINDOW_H + + +#include "guicast.h" +#include "nbody.h" + +class N_BodyDrag; +class N_BodyReset; +class NBodyModeItems; +class N_BodySetMode; +class NBodyDemoItems; +class N_BodySetDemo; +class NBodyNumBodyItems; +class N_BodyNumBodies; +class N_BodyWindow; + +class N_BodyDrag : public BC_CheckBox +{ +public: + N_BodyDrag(N_BodyWindow *gui, int x, int y); + + int handle_event(); + N_BodyWindow *gui; +}; + +class N_BodyReset : public BC_GenericButton +{ +public: + N_BodyReset(N_BodyWindow *gui, int x, int y); + ~N_BodyReset(); + int handle_event(); + + N_BodyWindow *gui; +}; + +class NBodyModeItems : public ArrayList +{ +public: + NBodyModeItems() {} + ~NBodyModeItems() { remove_all_objects(); } +}; + +class N_BodySetMode : public BC_PopupTextBox +{ +public: + N_BodySetMode(N_BodyWindow *gui, int x, int y, const char *text); + void create_objects(); + int handle_event(); + + N_BodyWindow *gui; + NBodyModeItems mode_items; +}; + +class NBodyDemoItems : public ArrayList +{ +public: + NBodyDemoItems() {} + ~NBodyDemoItems() { remove_all_objects(); } +}; + +class N_BodySetDemo : public BC_PopupTextBox +{ +public: + N_BodySetDemo(N_BodyWindow *gui, int x, int y, const char *text); + void create_objects(); + int handle_event(); + + N_BodyWindow *gui; + NBodyDemoItems demo_items; +}; + +class NBodyNumBodyItems : public ArrayList +{ +public: + NBodyNumBodyItems() {} + ~NBodyNumBodyItems() { remove_all_objects(); } +}; + +class N_BodyNumBodies : public BC_PopupTextBox +{ +public: + N_BodyNumBodies(N_BodyWindow *gui, int x, int y, const char *text); + void create_objects(); + int handle_event(); + + N_BodyWindow *gui; + NBodyNumBodyItems num_body_items; +}; + + +class N_BodyWindow : public PluginClientWindow +{ +public: + N_BodyWindow(N_BodyMain *plugin); + ~N_BodyWindow(); + + void create_objects(); + void update_gui(); + + int grab_event(XEvent *event); + int do_grab_event(XEvent *event); + void done_event(int result); + void send_configure_change(); + + N_BodyMain *plugin; + N_BodySetMode *set_mode; + N_BodySetDemo *set_demo; + N_BodyNumBodies *num_bodies; + N_BodyDrag *drag; + N_BodyReset *reset; + + int press_x, press_y; + int button_no, pending_config; +}; + +#endif diff --git a/cinelerra-5.1/plugins/nbodycuda/renders.C b/cinelerra-5.1/plugins/nbodycuda/renders.C new file mode 100644 index 00000000..82d669d5 --- /dev/null +++ b/cinelerra-5.1/plugins/nbodycuda/renders.C @@ -0,0 +1 @@ +#include "5_Simulations/nbody/render_particles.cpp" diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/cin_icon_rec.png b/cinelerra-5.1/plugins/theme_cakewalk/data/cin_icon_rec.png index 2c658a22..61188c40 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/cin_icon_rec.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/cin_icon_rec.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/cin_icon_vwin.png b/cinelerra-5.1/plugins/theme_cakewalk/data/cin_icon_vwin.png index c693d1b1..525815bb 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/cin_icon_vwin.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/cin_icon_vwin.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/heroine_icon.png b/cinelerra-5.1/plugins/theme_cakewalk/data/heroine_icon.png index 75af9274..1384edc9 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/heroine_icon.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/heroine_icon.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/in_checked.png b/cinelerra-5.1/plugins/theme_cakewalk/data/in_checked.png index 63a3c45b..7215c03f 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/in_checked.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/in_checked.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/in_checkedhi.png b/cinelerra-5.1/plugins/theme_cakewalk/data/in_checkedhi.png index 759df58f..9318fb7d 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/in_checkedhi.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/in_checkedhi.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/in_dn.png b/cinelerra-5.1/plugins/theme_cakewalk/data/in_dn.png index 9ad33eac..62e0c949 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/in_dn.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/in_dn.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/in_hi.png b/cinelerra-5.1/plugins/theme_cakewalk/data/in_hi.png index c020c336..59d58aaf 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/in_hi.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/in_hi.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/in_up.png b/cinelerra-5.1/plugins/theme_cakewalk/data/in_up.png index 6bdccf32..6a8bb8c3 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/in_up.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/in_up.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/inpoint.png b/cinelerra-5.1/plugins/theme_cakewalk/data/inpoint.png index 960cfbc6..9a99cc2e 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/inpoint.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/inpoint.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/label_checked.png b/cinelerra-5.1/plugins/theme_cakewalk/data/label_checked.png index ada0e5b0..3b6016d3 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/label_checked.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/label_checked.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/label_checkedhi.png b/cinelerra-5.1/plugins/theme_cakewalk/data/label_checkedhi.png index 43334e9a..1f7b260f 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/label_checkedhi.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/label_checkedhi.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_dn.png b/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_dn.png index d3c7ca8a..11cc3e7a 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_dn.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_dn.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_up.png b/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_up.png index e7769c3b..f697b71b 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_up.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_up.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_uphi.png b/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_uphi.png index c521b8c1..7ae1f93d 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_uphi.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/labeltoggle_uphi.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/out_checked.png b/cinelerra-5.1/plugins/theme_cakewalk/data/out_checked.png index b2289b00..0f1eb065 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/out_checked.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/out_checked.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/out_checkedhi.png b/cinelerra-5.1/plugins/theme_cakewalk/data/out_checkedhi.png index d6a181fd..d3e551be 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/out_checkedhi.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/out_checkedhi.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/out_dn.png b/cinelerra-5.1/plugins/theme_cakewalk/data/out_dn.png index 983d9942..62b714ec 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/out_dn.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/out_dn.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/out_hi.png b/cinelerra-5.1/plugins/theme_cakewalk/data/out_hi.png index 2143e29d..260bc41a 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/out_hi.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/out_hi.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/out_up.png b/cinelerra-5.1/plugins/theme_cakewalk/data/out_up.png index 4800f3b5..718d0ce2 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/out_up.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/out_up.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/outpoint.png b/cinelerra-5.1/plugins/theme_cakewalk/data/outpoint.png index 5b027021..db68b792 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/outpoint.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/outpoint.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/pot_dn.png b/cinelerra-5.1/plugins/theme_cakewalk/data/pot_dn.png index 0a2989d3..0ad7f75d 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/pot_dn.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/pot_dn.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/pot_hi.png b/cinelerra-5.1/plugins/theme_cakewalk/data/pot_hi.png index 0a00a5f7..70902f72 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/pot_hi.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/pot_hi.png differ diff --git a/cinelerra-5.1/plugins/theme_cakewalk/data/pot_up.png b/cinelerra-5.1/plugins/theme_cakewalk/data/pot_up.png index ab98ced7..4517f244 100644 Binary files a/cinelerra-5.1/plugins/theme_cakewalk/data/pot_up.png and b/cinelerra-5.1/plugins/theme_cakewalk/data/pot_up.png differ diff --git a/cinelerra-5.1/thirdparty/Makefile b/cinelerra-5.1/thirdparty/Makefile index 046a560b..acaf4efa 100644 --- a/cinelerra-5.1/thirdparty/Makefile +++ b/cinelerra-5.1/thirdparty/Makefile @@ -113,6 +113,7 @@ ffmpeg.cfg_params= \ --enable-pthreads --enable-gpl --disable-ffplay \ $(if $(WANT_VAAPI),--enable-vaapi,--disable-vaapi) \ $(if $(WANT_VDPAU),--enable-vdpau,--disable-vdpau) \ + $(if $(WANT_NV), --enable-nvenc --enable-nvdec) \ $(call if_pkg,twolame,--enable-libtwolame) \ $(call if_pkg,openjpeg,--enable-libopenjpeg) \ $(call if_pkg,lame,--enable-libmp3lame) \ @@ -125,6 +126,7 @@ ffmpeg.cfg_params= \ $(call if_pkg,x264,--enable-libx264) \ $(call if_pkg,x265,--enable-libx265) \ --extra-cflags="\ + $(if $(WANT_NV), $(inc_ffnvcodec)) \ $(call inc_path,twolame,libtwolame) \ $(call inc_path,lame,include) \ $(call inc_path,libaom,usr/local/include) \ @@ -289,7 +291,9 @@ $(call rules,$(call std-build,djbfft)) $(call rules,$(call std-build,audiofile)) $(call rules,$(call std-build,encore)) $(call rules,$(call std-build,esound,audiofile)) -$(call rules,$(call std-build,ffmpeg, twolame lame openjpeg opus libtheora x264 x265 libvpx libaom libwebp)) +$(call rules,$(call std-build,ffmpeg, twolame lame openjpeg opus \ + libtheora x264 x265 libvpx libaom libwebp \ + $(if $(WANT_NV), ffnvcodec))) $(call rules,$(call std-build,fftw)) $(call rules,$(call std-build,flac,libogg)) $(call rules,$(call std-build,giflib)) @@ -325,6 +329,7 @@ $(call rules,$(call std-build,sord, serd)) $(call rules,$(call std-build,sratom, serd sord lv2)) $(call rules,$(call std-build,lilv, lv2 sratom serd sord)) $(call rules,$(call std-build,suil, lv2)) +$(call rules,$(call std-build,ffnvcodec)) # specialize festival, multiple tarballs festival: diff --git a/cinelerra-5.1/thirdparty/downloads.txt b/cinelerra-5.1/thirdparty/downloads.txt index b998f814..2b0c152b 100644 --- a/cinelerra-5.1/thirdparty/downloads.txt +++ b/cinelerra-5.1/thirdparty/downloads.txt @@ -36,6 +36,7 @@ https://github.com/swh/ladspa/releases/tag/v0.4.17, plugin.org.uk https://archive.mozilla.org/pub/opus/opus-1.3.tar.gz https://github.com/webmproject/libwebp = libwebp-1.0.2 https://github.com/mozilla/aom = libaom-v1.0.0 +git clone https://git.videolan.org/git/ffmpeg/nv-codec-headers.git https://gitlab.com/drobilla/lv2/-/archive/v1.16.0/lv2-v1.16.0.tar.gz http://download.drobilla.net/suil-0.10.2.tar.bz2 diff --git a/cinelerra-5.1/thirdparty/src/ffnvcodec.tar.xz b/cinelerra-5.1/thirdparty/src/ffnvcodec.tar.xz new file mode 100644 index 00000000..00bc94a5 Binary files /dev/null and b/cinelerra-5.1/thirdparty/src/ffnvcodec.tar.xz differ