");
+ addClass(this.panel.parentNode, this.clsMode);
+ }
+ css(document.documentElement, "overflowY", this.overlay ? "hidden" : "");
+ addClass(document.body, this.clsContainer, this.clsFlip);
+ css(this.$el, "display", "block");
+ addClass(this.$el, this.clsOverlay);
+ addClass(this.panel, this.clsSidebarAnimation, this.mode !== "reveal" ? this.clsMode : "");
+ height(document.body);
+ addClass(document.body, this.clsContainerAnimation);
+ this.clsContainerAnimation && suppressUserScale();
+ }
+ }, {
+ name: "hide",
+ self: true,
+ handler: function() {
+ removeClass(document.body, this.clsContainerAnimation);
+ var active = this.getActive();
+ if (this.mode === "none" || active && active !== this && active !== this.prev) {
+ trigger(this.panel, "transitionend");
+ }
+ }
+ }, {
+ name: "hidden",
+ self: true,
+ handler: function() {
+ this.clsContainerAnimation && resumeUserScale();
+ if (this.mode === "reveal") {
+ unwrap(this.panel);
+ }
+ removeClass(this.panel, this.clsSidebarAnimation, this.clsMode);
+ removeClass(this.$el, this.clsOverlay);
+ css(this.$el, "display", "");
+ removeClass(document.body, this.clsContainer, this.clsFlip);
+ css(document.documentElement, "overflowY", "");
+ }
+ }, {
+ name: "swipeLeft swipeRight",
+ handler: function(e) {
+ if (this.isToggled() && isTouch(e) && e.type === "swipeLeft" ^ this.flip) {
+ this.hide();
+ }
+ }
+ } ]
+ };
+ function suppressUserScale() {
+ getViewport().content += ",user-scalable=0";
+ }
+ function resumeUserScale() {
+ var viewport = getViewport();
+ viewport.content = viewport.content.replace(/,user-scalable=0$/, "");
+ }
+ function getViewport() {
+ return $('meta[name="viewport"]', document.head) || append(document.head, '
');
+ }
+ var OverflowAuto = {
+ mixins: [ Class ],
+ props: {
+ selContainer: String,
+ selContent: String
+ },
+ data: {
+ selContainer: ".uk-modal",
+ selContent: ".uk-modal-dialog"
+ },
+ computed: {
+ container: function(ref, $el) {
+ var selContainer = ref.selContainer;
+ return closest($el, selContainer);
+ },
+ content: function(ref, $el) {
+ var selContent = ref.selContent;
+ return closest($el, selContent);
+ }
+ },
+ connected: function() {
+ css(this.$el, "minHeight", 150);
+ },
+ update: {
+ read: function() {
+ if (!this.content || !this.container) {
+ return false;
+ }
+ return {
+ current: toFloat(css(this.$el, "maxHeight")),
+ max: Math.max(150, height(this.container) - (offset(this.content).height - height(this.$el)))
+ };
+ },
+ write: function(ref) {
+ var current = ref.current;
+ var max = ref.max;
+ css(this.$el, "maxHeight", max);
+ if (Math.round(current) !== Math.round(max)) {
+ trigger(this.$el, "resize");
+ }
+ },
+ events: [ "resize" ]
+ }
+ };
+ var Responsive = {
+ props: [ "width", "height" ],
+ connected: function() {
+ addClass(this.$el, "uk-responsive-width");
+ },
+ update: {
+ read: function() {
+ return isVisible(this.$el) && this.width && this.height ? {
+ width: width(this.$el.parentNode),
+ height: this.height
+ } : false;
+ },
+ write: function(dim) {
+ height(this.$el, Dimensions.contain({
+ height: this.height,
+ width: this.width
+ }, dim).height);
+ },
+ events: [ "resize" ]
+ }
+ };
+ var Scroll = {
+ props: {
+ duration: Number,
+ offset: Number
+ },
+ data: {
+ duration: 1e3,
+ offset: 0
+ },
+ methods: {
+ scrollTo: function(el) {
+ var this$1 = this;
+ el = el && $(el) || document.body;
+ var docHeight = height(document);
+ var winHeight = height(window);
+ var target = offset(el).top - this.offset;
+ if (target + winHeight > docHeight) {
+ target = docHeight - winHeight;
+ }
+ if (!trigger(this.$el, "beforescroll", [ this, el ])) {
+ return;
+ }
+ var start = Date.now();
+ var startY = window.pageYOffset;
+ var step = function() {
+ var currentY = startY + (target - startY) * ease(clamp((Date.now() - start) / this$1.duration));
+ scrollTop(window, currentY);
+ if (currentY !== target) {
+ requestAnimationFrame(step);
+ } else {
+ trigger(this$1.$el, "scrolled", [ this$1, el ]);
+ }
+ };
+ step();
+ }
+ },
+ events: {
+ click: function(e) {
+ if (e.defaultPrevented) {
+ return;
+ }
+ e.preventDefault();
+ this.scrollTo(escape(decodeURIComponent(this.$el.hash)).substr(1));
+ }
+ }
+ };
+ function ease(k) {
+ return .5 * (1 - Math.cos(Math.PI * k));
+ }
+ var Scrollspy = {
+ args: "cls",
+ props: {
+ cls: "list",
+ target: String,
+ hidden: Boolean,
+ offsetTop: Number,
+ offsetLeft: Number,
+ repeat: Boolean,
+ delay: Number
+ },
+ data: function() {
+ return {
+ cls: [],
+ target: false,
+ hidden: true,
+ offsetTop: 0,
+ offsetLeft: 0,
+ repeat: false,
+ delay: 0,
+ inViewClass: "uk-scrollspy-inview"
+ };
+ },
+ computed: {
+ elements: function(ref, $el) {
+ var target = ref.target;
+ return target ? $$(target, $el) : [ $el ];
+ }
+ },
+ update: [ {
+ write: function() {
+ if (this.hidden) {
+ css(filter(this.elements, ":not(." + this.inViewClass + ")"), "visibility", "hidden");
+ }
+ }
+ }, {
+ read: function(els) {
+ var this$1 = this;
+ if (!els.update) {
+ return;
+ }
+ this.elements.forEach(function(el, i) {
+ var elData = els[i];
+ if (!elData || elData.el !== el) {
+ var cls = data(el, "uk-scrollspy-class");
+ elData = {
+ el: el,
+ toggles: cls && cls.split(",") || this$1.cls
+ };
+ }
+ elData.show = isInView(el, this$1.offsetTop, this$1.offsetLeft);
+ els[i] = elData;
+ });
+ },
+ write: function(els) {
+ var this$1 = this;
+ if (!els.update) {
+ this.$emit();
+ return els.update = true;
+ }
+ this.elements.forEach(function(el, i) {
+ var elData = els[i];
+ var cls = elData.toggles[i] || elData.toggles[0];
+ if (elData.show && !elData.inview && !elData.queued) {
+ var show = function() {
+ css(el, "visibility", "");
+ addClass(el, this$1.inViewClass);
+ toggleClass(el, cls);
+ trigger(el, "inview");
+ this$1.$update(el);
+ elData.inview = true;
+ elData.abort && elData.abort();
+ };
+ if (this$1.delay) {
+ elData.queued = true;
+ els.promise = (els.promise || Promise.resolve()).then(function() {
+ return !elData.inview && new Promise(function(resolve) {
+ var timer = setTimeout(function() {
+ show();
+ resolve();
+ }, els.promise || this$1.elements.length === 1 ? this$1.delay : 0);
+ elData.abort = function() {
+ clearTimeout(timer);
+ resolve();
+ elData.queued = false;
+ };
+ });
+ });
+ } else {
+ show();
+ }
+ } else if (!elData.show && (elData.inview || elData.queued) && this$1.repeat) {
+ elData.abort && elData.abort();
+ if (!elData.inview) {
+ return;
+ }
+ css(el, "visibility", this$1.hidden ? "hidden" : "");
+ removeClass(el, this$1.inViewClass);
+ toggleClass(el, cls);
+ trigger(el, "outview");
+ this$1.$update(el);
+ elData.inview = false;
+ }
+ });
+ },
+ events: [ "scroll", "resize" ]
+ } ]
+ };
+ var ScrollspyNav = {
+ props: {
+ cls: String,
+ closest: String,
+ scroll: Boolean,
+ overflow: Boolean,
+ offset: Number
+ },
+ data: {
+ cls: "uk-active",
+ closest: false,
+ scroll: false,
+ overflow: true,
+ offset: 0
+ },
+ computed: {
+ links: function(_, $el) {
+ return $$('a[href^="#"]', $el).filter(function(el) {
+ return el.hash;
+ });
+ },
+ elements: function(ref) {
+ var selector = ref.closest;
+ return closest(this.links, selector || "*");
+ },
+ targets: function() {
+ return $$(this.links.map(function(el) {
+ return el.hash;
+ }).join(","));
+ }
+ },
+ update: [ {
+ read: function() {
+ if (this.scroll) {
+ this.$create("scroll", this.links, {
+ offset: this.offset || 0
+ });
+ }
+ }
+ }, {
+ read: function(data$$1) {
+ var this$1 = this;
+ var scroll = window.pageYOffset + this.offset + 1;
+ var max = height(document) - height(window) + this.offset;
+ data$$1.active = false;
+ this.targets.every(function(el, i) {
+ var ref = offset(el);
+ var top = ref.top;
+ var last = i + 1 === this$1.targets.length;
+ if (!this$1.overflow && (i === 0 && top > scroll || last && top + el.offsetTop < scroll)) {
+ return false;
+ }
+ if (!last && offset(this$1.targets[i + 1]).top <= scroll) {
+ return true;
+ }
+ if (scroll >= max) {
+ for (var j = this$1.targets.length - 1; j > i; j--) {
+ if (isInView(this$1.targets[j])) {
+ el = this$1.targets[j];
+ break;
+ }
+ }
+ }
+ return !(data$$1.active = $(filter(this$1.links, '[href="#' + el.id + '"]')));
+ });
+ },
+ write: function(ref) {
+ var active = ref.active;
+ this.links.forEach(function(el) {
+ return el.blur();
+ });
+ removeClass(this.elements, this.cls);
+ if (active) {
+ trigger(this.$el, "active", [ active, addClass(this.closest ? closest(active, this.closest) : active, this.cls) ]);
+ }
+ },
+ events: [ "scroll", "resize" ]
+ } ]
+ };
+ var Sticky = {
+ mixins: [ Class, Media ],
+ props: {
+ top: null,
+ bottom: Boolean,
+ offset: Number,
+ animation: String,
+ clsActive: String,
+ clsInactive: String,
+ clsFixed: String,
+ clsBelow: String,
+ selTarget: String,
+ widthElement: Boolean,
+ showOnUp: Boolean,
+ targetOffset: Number
+ },
+ data: {
+ top: 0,
+ bottom: false,
+ offset: 0,
+ animation: "",
+ clsActive: "uk-active",
+ clsInactive: "",
+ clsFixed: "uk-sticky-fixed",
+ clsBelow: "uk-sticky-below",
+ selTarget: "",
+ widthElement: false,
+ showOnUp: false,
+ targetOffset: false
+ },
+ computed: {
+ selTarget: function(ref, $el) {
+ var selTarget = ref.selTarget;
+ return selTarget && $(selTarget, $el) || $el;
+ },
+ widthElement: function(ref, $el) {
+ var widthElement = ref.widthElement;
+ return query(widthElement, $el) || this.placeholder;
+ },
+ isActive: {
+ get: function() {
+ return hasClass(this.selTarget, this.clsActive);
+ },
+ set: function(value) {
+ if (value && !this.isActive) {
+ replaceClass(this.selTarget, this.clsInactive, this.clsActive);
+ trigger(this.$el, "active");
+ } else if (!value && !hasClass(this.selTarget, this.clsInactive)) {
+ replaceClass(this.selTarget, this.clsActive, this.clsInactive);
+ trigger(this.$el, "inactive");
+ }
+ }
+ }
+ },
+ connected: function() {
+ this.placeholder = $("+ .uk-sticky-placeholder", this.$el) || $('
');
+ this.isFixed = false;
+ this.isActive = false;
+ },
+ disconnected: function() {
+ if (this.isFixed) {
+ this.hide();
+ removeClass(this.selTarget, this.clsInactive);
+ }
+ remove(this.placeholder);
+ this.placeholder = null;
+ this.widthElement = null;
+ },
+ events: [ {
+ name: "load hashchange popstate",
+ el: window,
+ handler: function() {
+ var this$1 = this;
+ if (!(this.targetOffset !== false && location.hash && window.pageYOffset > 0)) {
+ return;
+ }
+ var target = $(location.hash);
+ if (target) {
+ fastdom.read(function() {
+ var ref = offset(target);
+ var top = ref.top;
+ var elTop = offset(this$1.$el).top;
+ var elHeight = this$1.$el.offsetHeight;
+ if (this$1.isFixed && elTop + elHeight >= top && elTop <= top + target.offsetHeight) {
+ scrollTop(window, top - elHeight - (isNumeric(this$1.targetOffset) ? this$1.targetOffset : 0) - this$1.offset);
+ }
+ });
+ }
+ }
+ } ],
+ update: [ {
+ read: function(ref, type) {
+ var height$$1 = ref.height;
+ if (this.isActive && type !== "update") {
+ this.hide();
+ height$$1 = this.$el.offsetHeight;
+ this.show();
+ }
+ height$$1 = !this.isActive ? this.$el.offsetHeight : height$$1;
+ this.topOffset = offset(this.isFixed ? this.placeholder : this.$el).top;
+ this.bottomOffset = this.topOffset + height$$1;
+ var bottom = parseProp("bottom", this);
+ this.top = Math.max(toFloat(parseProp("top", this)), this.topOffset) - this.offset;
+ this.bottom = bottom && bottom - height$$1;
+ this.inactive = !this.matchMedia;
+ return {
+ lastScroll: false,
+ height: height$$1,
+ margins: css(this.$el, [ "marginTop", "marginBottom", "marginLeft", "marginRight" ])
+ };
+ },
+ write: function(ref) {
+ var height$$1 = ref.height;
+ var margins = ref.margins;
+ var ref$1 = this;
+ var placeholder = ref$1.placeholder;
+ css(placeholder, assign({
+ height: height$$1
+ }, margins));
+ if (!within(placeholder, document)) {
+ after(this.$el, placeholder);
+ attr(placeholder, "hidden", "");
+ }
+ this.isActive = this.isActive;
+ },
+ events: [ "resize" ]
+ }, {
+ read: function(ref) {
+ var scroll = ref.scroll;
+ if (scroll === void 0) scroll = 0;
+ this.width = (isVisible(this.widthElement) ? this.widthElement : this.$el).offsetWidth;
+ this.scroll = window.pageYOffset;
+ return {
+ dir: scroll <= this.scroll ? "down" : "up",
+ scroll: this.scroll,
+ visible: isVisible(this.$el),
+ top: offsetPosition(this.placeholder)[0]
+ };
+ },
+ write: function(data$$1, type) {
+ var this$1 = this;
+ var initTimestamp = data$$1.initTimestamp;
+ if (initTimestamp === void 0) initTimestamp = 0;
+ var dir = data$$1.dir;
+ var lastDir = data$$1.lastDir;
+ var lastScroll = data$$1.lastScroll;
+ var scroll = data$$1.scroll;
+ var top = data$$1.top;
+ var visible = data$$1.visible;
+ var now = performance.now();
+ data$$1.lastScroll = scroll;
+ if (scroll < 0 || scroll === lastScroll || !visible || this.disabled || this.showOnUp && type !== "scroll") {
+ return;
+ }
+ if (now - initTimestamp > 300 || dir !== lastDir) {
+ data$$1.initScroll = scroll;
+ data$$1.initTimestamp = now;
+ }
+ data$$1.lastDir = dir;
+ if (this.showOnUp && Math.abs(data$$1.initScroll - scroll) <= 30 && Math.abs(lastScroll - scroll) <= 10) {
+ return;
+ }
+ if (this.inactive || scroll < this.top || this.showOnUp && (scroll <= this.top || dir === "down" || dir === "up" && !this.isFixed && scroll <= this.bottomOffset)) {
+ if (!this.isFixed) {
+ if (Animation.inProgress(this.$el) && top > scroll) {
+ Animation.cancel(this.$el);
+ this.hide();
+ }
+ return;
+ }
+ this.isFixed = false;
+ if (this.animation && scroll > this.topOffset) {
+ Animation.cancel(this.$el);
+ Animation.out(this.$el, this.animation).then(function() {
+ return this$1.hide();
+ }, noop);
+ } else {
+ this.hide();
+ }
+ } else if (this.isFixed) {
+ this.update();
+ } else if (this.animation) {
+ Animation.cancel(this.$el);
+ this.show();
+ Animation.in(this.$el, this.animation).catch(noop);
+ } else {
+ this.show();
+ }
+ },
+ events: [ "resize", "scroll" ]
+ } ],
+ methods: {
+ show: function() {
+ this.isFixed = true;
+ this.update();
+ attr(this.placeholder, "hidden", null);
+ },
+ hide: function() {
+ this.isActive = false;
+ removeClass(this.$el, this.clsFixed, this.clsBelow);
+ css(this.$el, {
+ position: "",
+ top: "",
+ width: ""
+ });
+ attr(this.placeholder, "hidden", "");
+ },
+ update: function() {
+ var active = this.top !== 0 || this.scroll > this.top;
+ var top = Math.max(0, this.offset);
+ if (this.bottom && this.scroll > this.bottom - this.offset) {
+ top = this.bottom - this.scroll;
+ }
+ css(this.$el, {
+ position: "fixed",
+ top: top + "px",
+ width: this.width
+ });
+ this.isActive = active;
+ toggleClass(this.$el, this.clsBelow, this.scroll > this.bottomOffset);
+ addClass(this.$el, this.clsFixed);
+ }
+ }
+ };
+ function parseProp(prop, ref) {
+ var $props = ref.$props;
+ var $el = ref.$el;
+ var propOffset = ref[prop + "Offset"];
+ var value = $props[prop];
+ if (!value) {
+ return;
+ }
+ if (isNumeric(value)) {
+ return propOffset + toFloat(value);
+ } else if (isString(value) && value.match(/^-?\d+vh$/)) {
+ return height(window) * toFloat(value) / 100;
+ } else {
+ var el = value === true ? $el.parentNode : query(value, $el);
+ if (el) {
+ return offset(el).top + el.offsetHeight;
+ }
+ }
+ }
+ var Switcher = {
+ mixins: [ Togglable ],
+ args: "connect",
+ props: {
+ connect: String,
+ toggle: String,
+ active: Number,
+ swiping: Boolean
+ },
+ data: {
+ connect: "~.uk-switcher",
+ toggle: "> * > :first-child",
+ active: 0,
+ swiping: true,
+ cls: "uk-active",
+ clsContainer: "uk-switcher",
+ attrItem: "uk-switcher-item",
+ queued: true
+ },
+ computed: {
+ connects: function(ref, $el) {
+ var connect = ref.connect;
+ return queryAll(connect, $el);
+ },
+ toggles: function(ref, $el) {
+ var toggle = ref.toggle;
+ return $$(toggle, $el);
+ }
+ },
+ events: [ {
+ name: "click",
+ delegate: function() {
+ return this.toggle + ":not(.uk-disabled)";
+ },
+ handler: function(e) {
+ e.preventDefault();
+ this.show(toNodes(this.$el.children).filter(function(el) {
+ return within(e.current, el);
+ })[0]);
+ }
+ }, {
+ name: "click",
+ el: function() {
+ return this.connects;
+ },
+ delegate: function() {
+ return "[" + this.attrItem + "],[data-" + this.attrItem + "]";
+ },
+ handler: function(e) {
+ e.preventDefault();
+ this.show(data(e.current, this.attrItem));
+ }
+ }, {
+ name: "swipeRight swipeLeft",
+ filter: function() {
+ return this.swiping;
+ },
+ el: function() {
+ return this.connects;
+ },
+ handler: function(e) {
+ if (!isTouch(e)) {
+ return;
+ }
+ e.preventDefault();
+ if (!window.getSelection().toString()) {
+ this.show(e.type === "swipeLeft" ? "next" : "previous");
+ }
+ }
+ } ],
+ update: function() {
+ var this$1 = this;
+ this.connects.forEach(function(list) {
+ return this$1.updateAria(list.children);
+ });
+ var ref = this.$el;
+ var children = ref.children;
+ this.show(filter(children, "." + this.cls)[0] || children[this.active] || children[0]);
+ },
+ methods: {
+ index: function() {
+ return !!this.connects.length && index(filter(this.connects[0].children, "." + this.cls)[0]);
+ },
+ show: function(item) {
+ var this$1 = this;
+ var ref = this.$el;
+ var children = ref.children;
+ var length = children.length;
+ var prev = this.index();
+ var hasPrev = prev >= 0;
+ var dir = item === "previous" ? -1 : 1;
+ var toggle, active, next = getIndex(item, children, prev);
+ for (var i = 0; i < length; i++, next = (next + dir + length) % length) {
+ if (!matches(this.toggles[next], ".uk-disabled *, .uk-disabled, [disabled]")) {
+ toggle = this.toggles[next];
+ active = children[next];
+ break;
+ }
+ }
+ if (!active || prev >= 0 && hasClass(active, this.cls) || prev === next) {
+ return;
+ }
+ removeClass(children, this.cls);
+ addClass(active, this.cls);
+ attr(this.toggles, "aria-expanded", false);
+ attr(toggle, "aria-expanded", true);
+ this.connects.forEach(function(list) {
+ if (!hasPrev) {
+ this$1.toggleNow(list.children[next]);
+ } else {
+ this$1.toggleElement([ list.children[prev], list.children[next] ]);
+ }
+ });
+ }
+ }
+ };
+ var Tab = {
+ mixins: [ Class ],
+ extends: Switcher,
+ props: {
+ media: Boolean
+ },
+ data: {
+ media: 960,
+ attrItem: "uk-tab-item"
+ },
+ connected: function() {
+ var cls = hasClass(this.$el, "uk-tab-left") ? "uk-tab-left" : hasClass(this.$el, "uk-tab-right") ? "uk-tab-right" : false;
+ if (cls) {
+ this.$create("toggle", this.$el, {
+ cls: cls,
+ mode: "media",
+ media: this.media
+ });
+ }
+ }
+ };
+ var Toggle = {
+ mixins: [ Media, Togglable ],
+ args: "target",
+ props: {
+ href: String,
+ target: null,
+ mode: "list"
+ },
+ data: {
+ href: false,
+ target: false,
+ mode: "click",
+ queued: true
+ },
+ computed: {
+ target: function(ref, $el) {
+ var href = ref.href;
+ var target = ref.target;
+ target = queryAll(target || href, $el);
+ return target.length && target || [ $el ];
+ }
+ },
+ connected: function() {
+ trigger(this.target, "updatearia", [ this ]);
+ },
+ events: [ {
+ name: pointerEnter + " " + pointerLeave,
+ filter: function() {
+ return includes(this.mode, "hover");
+ },
+ handler: function(e) {
+ if (!isTouch(e)) {
+ this.toggle("toggle" + (e.type === pointerEnter ? "show" : "hide"));
+ }
+ }
+ }, {
+ name: "click",
+ filter: function() {
+ return includes(this.mode, "click") || hasTouch && includes(this.mode, "hover");
+ },
+ handler: function(e) {
+ if (!isTouch(e) && !includes(this.mode, "click")) {
+ return;
+ }
+ var link;
+ if (closest(e.target, 'a[href="#"], a[href=""], button') || (link = closest(e.target, "a[href]")) && (this.cls || !isVisible(this.target) || link.hash && matches(this.target, link.hash))) {
+ e.preventDefault();
+ }
+ this.toggle();
+ }
+ } ],
+ update: {
+ write: function() {
+ if (!includes(this.mode, "media") || !this.media) {
+ return;
+ }
+ var toggled = this.isToggled(this.target);
+ if (this.matchMedia ? !toggled : toggled) {
+ this.toggle();
+ }
+ },
+ events: [ "resize" ]
+ },
+ methods: {
+ toggle: function(type) {
+ if (trigger(this.target, type || "toggle", [ this ])) {
+ this.toggleElement(this.target);
+ }
+ }
+ }
+ };
+ function core(UIkit) {
+ UIkit.component("accordion", Accordion);
+ UIkit.component("alert", Alert);
+ UIkit.component("cover", Cover);
+ UIkit.component("drop", Drop);
+ UIkit.component("dropdown", Dropdown);
+ UIkit.component("formCustom", FormCustom);
+ UIkit.component("gif", Gif);
+ UIkit.component("grid", Grid);
+ UIkit.component("heightMatch", HeightMatch);
+ UIkit.component("heightViewport", HeightViewport);
+ UIkit.component("icon", Icon);
+ UIkit.component("img", Img);
+ UIkit.component("leader", Leader);
+ UIkit.component("margin", Margin);
+ UIkit.component("modal", Modal$1);
+ UIkit.component("nav", Nav);
+ UIkit.component("navbar", Navbar);
+ UIkit.component("offcanvas", Offcanvas);
+ UIkit.component("overflowAuto", OverflowAuto);
+ UIkit.component("responsive", Responsive);
+ UIkit.component("scroll", Scroll);
+ UIkit.component("scrollspy", Scrollspy);
+ UIkit.component("scrollspyNav", ScrollspyNav);
+ UIkit.component("sticky", Sticky);
+ UIkit.component("svg", SVG);
+ UIkit.component("switcher", Switcher);
+ UIkit.component("tab", Tab);
+ UIkit.component("toggle", Toggle);
+ UIkit.component("video", Video);
+ UIkit.component("close", Close);
+ UIkit.component("marker", IconComponent);
+ UIkit.component("navbarToggleIcon", IconComponent);
+ UIkit.component("overlayIcon", IconComponent);
+ UIkit.component("paginationNext", IconComponent);
+ UIkit.component("paginationPrevious", IconComponent);
+ UIkit.component("searchIcon", Search);
+ UIkit.component("slidenavNext", Slidenav);
+ UIkit.component("slidenavPrevious", Slidenav);
+ UIkit.component("spinner", Spinner);
+ UIkit.component("totop", IconComponent);
+ UIkit.use(Core);
+ }
+ UIkit.version = "3.0.3";
+ core(UIkit);
+ var Countdown = {
+ mixins: [ Class ],
+ props: {
+ date: String,
+ clsWrapper: String
+ },
+ data: {
+ date: "",
+ clsWrapper: ".uk-countdown-%unit%"
+ },
+ computed: {
+ date: function(ref) {
+ var date = ref.date;
+ return Date.parse(date);
+ },
+ days: function(ref, $el) {
+ var clsWrapper = ref.clsWrapper;
+ return $(clsWrapper.replace("%unit%", "days"), $el);
+ },
+ hours: function(ref, $el) {
+ var clsWrapper = ref.clsWrapper;
+ return $(clsWrapper.replace("%unit%", "hours"), $el);
+ },
+ minutes: function(ref, $el) {
+ var clsWrapper = ref.clsWrapper;
+ return $(clsWrapper.replace("%unit%", "minutes"), $el);
+ },
+ seconds: function(ref, $el) {
+ var clsWrapper = ref.clsWrapper;
+ return $(clsWrapper.replace("%unit%", "seconds"), $el);
+ },
+ units: function() {
+ var this$1 = this;
+ return [ "days", "hours", "minutes", "seconds" ].filter(function(unit) {
+ return this$1[unit];
+ });
+ }
+ },
+ connected: function() {
+ this.start();
+ },
+ disconnected: function() {
+ var this$1 = this;
+ this.stop();
+ this.units.forEach(function(unit) {
+ return empty(this$1[unit]);
+ });
+ },
+ events: [ {
+ name: "visibilitychange",
+ el: document,
+ handler: function() {
+ if (document.hidden) {
+ this.stop();
+ } else {
+ this.start();
+ }
+ }
+ } ],
+ update: {
+ write: function() {
+ var this$1 = this;
+ var timespan = getTimeSpan(this.date);
+ if (timespan.total <= 0) {
+ this.stop();
+ timespan.days = timespan.hours = timespan.minutes = timespan.seconds = 0;
+ }
+ this.units.forEach(function(unit) {
+ var digits = String(Math.floor(timespan[unit]));
+ digits = digits.length < 2 ? "0" + digits : digits;
+ var el = this$1[unit];
+ if (el.textContent !== digits) {
+ digits = digits.split("");
+ if (digits.length !== el.children.length) {
+ html(el, digits.map(function() {
+ return "
";
+ }).join(""));
+ }
+ digits.forEach(function(digit, i) {
+ return el.children[i].textContent = digit;
+ });
+ }
+ });
+ }
+ },
+ methods: {
+ start: function() {
+ var this$1 = this;
+ this.stop();
+ if (this.date && this.units.length) {
+ this.$emit();
+ this.timer = setInterval(function() {
+ return this$1.$emit();
+ }, 1e3);
+ }
+ },
+ stop: function() {
+ if (this.timer) {
+ clearInterval(this.timer);
+ this.timer = null;
+ }
+ }
+ }
+ };
+ function getTimeSpan(date) {
+ var total = date - Date.now();
+ return {
+ total: total,
+ seconds: total / 1e3 % 60,
+ minutes: total / 1e3 / 60 % 60,
+ hours: total / 1e3 / 60 / 60 % 24,
+ days: total / 1e3 / 60 / 60 / 24
+ };
+ }
+ var targetClass = "uk-animation-target";
+ var Animate = {
+ props: {
+ animation: Number
+ },
+ data: {
+ animation: 150
+ },
+ computed: {
+ target: function() {
+ return this.$el;
+ }
+ },
+ methods: {
+ animate: function(action) {
+ var this$1 = this;
+ addStyle();
+ var children = toNodes(this.target.children);
+ var propsFrom = children.map(function(el) {
+ return getProps(el, true);
+ });
+ var oldHeight = height(this.target);
+ var oldScrollY = window.pageYOffset;
+ action();
+ Transition.cancel(this.target);
+ children.forEach(Transition.cancel);
+ reset(this.target);
+ this.$update(this.target);
+ fastdom.flush();
+ var newHeight = height(this.target);
+ children = children.concat(toNodes(this.target.children).filter(function(el) {
+ return !includes(children, el);
+ }));
+ var propsTo = children.map(function(el, i) {
+ return el.parentNode && i in propsFrom ? propsFrom[i] ? isVisible(el) ? getPositionWithMargin(el) : {
+ opacity: 0
+ } : {
+ opacity: isVisible(el) ? 1 : 0
+ } : false;
+ });
+ propsFrom = propsTo.map(function(props, i) {
+ var from = children[i].parentNode === this$1.target ? propsFrom[i] || getProps(children[i]) : false;
+ if (from) {
+ if (!props) {
+ delete from.opacity;
+ } else if (!("opacity" in props)) {
+ var opacity = from.opacity;
+ if (opacity % 1) {
+ props.opacity = 1;
+ } else {
+ delete from.opacity;
+ }
+ }
+ }
+ return from;
+ });
+ addClass(this.target, targetClass);
+ children.forEach(function(el, i) {
+ return propsFrom[i] && css(el, propsFrom[i]);
+ });
+ css(this.target, "height", oldHeight);
+ scrollTop(window, oldScrollY);
+ return Promise.all(children.map(function(el, i) {
+ return propsFrom[i] && propsTo[i] ? Transition.start(el, propsTo[i], this$1.animation, "ease") : Promise.resolve();
+ }).concat(Transition.start(this.target, {
+ height: newHeight
+ }, this.animation, "ease"))).then(function() {
+ children.forEach(function(el, i) {
+ return css(el, {
+ display: propsTo[i].opacity === 0 ? "none" : "",
+ zIndex: ""
+ });
+ });
+ reset(this$1.target);
+ this$1.$update(this$1.target);
+ fastdom.flush();
+ }, noop);
+ }
+ }
+ };
+ function getProps(el, opacity) {
+ var zIndex = css(el, "zIndex");
+ return isVisible(el) ? assign({
+ display: "",
+ opacity: opacity ? css(el, "opacity") : "0",
+ pointerEvents: "none",
+ position: "absolute",
+ zIndex: zIndex === "auto" ? index(el) : zIndex
+ }, getPositionWithMargin(el)) : false;
+ }
+ function reset(el) {
+ css(el.children, {
+ height: "",
+ left: "",
+ opacity: "",
+ pointerEvents: "",
+ position: "",
+ top: "",
+ width: ""
+ });
+ removeClass(el, targetClass);
+ css(el, "height", "");
+ }
+ function getPositionWithMargin(el) {
+ var ref = el.getBoundingClientRect();
+ var height$$1 = ref.height;
+ var width$$1 = ref.width;
+ var ref$1 = position(el);
+ var top = ref$1.top;
+ var left = ref$1.left;
+ top += toFloat(css(el, "marginTop"));
+ return {
+ top: top,
+ left: left,
+ height: height$$1,
+ width: width$$1
+ };
+ }
+ var style$1;
+ function addStyle() {
+ if (!style$1) {
+ style$1 = append(document.head, "
diff --git a/uploads/faq.svg b/uploads/faq.svg
new file mode 100644
index 0000000000..d4c3bbbb14
--- /dev/null
+++ b/uploads/faq.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/uploads/favicon.ico b/uploads/favicon.ico
new file mode 100644
index 0000000000..0202d6434c
Binary files /dev/null and b/uploads/favicon.ico differ
diff --git a/uploads/favicon.png b/uploads/favicon.png
new file mode 100644
index 0000000000..0202d6434c
Binary files /dev/null and b/uploads/favicon.png differ
diff --git a/uploads/fin.jpeg b/uploads/fin.jpeg
new file mode 100644
index 0000000000..c60e4b00a1
Binary files /dev/null and b/uploads/fin.jpeg differ
diff --git a/uploads/kai.png b/uploads/kai.png
new file mode 100644
index 0000000000..883a641c2f
Binary files /dev/null and b/uploads/kai.png differ
diff --git a/uploads/logo_projectforge.gif b/uploads/logo_projectforge.gif
new file mode 100644
index 0000000000..3fc622f904
Binary files /dev/null and b/uploads/logo_projectforge.gif differ
diff --git a/uploads/scalable.svg b/uploads/scalable.svg
new file mode 100644
index 0000000000..9975e643f4
--- /dev/null
+++ b/uploads/scalable.svg
@@ -0,0 +1 @@
+
\ No newline at end of file
diff --git a/uploads/screenshots/2022-Calendar.png b/uploads/screenshots/2022-Calendar.png
new file mode 100644
index 0000000000..9c0477b09c
Binary files /dev/null and b/uploads/screenshots/2022-Calendar.png differ
diff --git a/uploads/screenshots/2022-Datatransfer.png b/uploads/screenshots/2022-Datatransfer.png
new file mode 100644
index 0000000000..26954f301e
Binary files /dev/null and b/uploads/screenshots/2022-Datatransfer.png differ
diff --git a/uploads/screenshots/2022-Skillmatrix.png b/uploads/screenshots/2022-Skillmatrix.png
new file mode 100644
index 0000000000..7064557ff3
Binary files /dev/null and b/uploads/screenshots/2022-Skillmatrix.png differ
diff --git a/uploads/screenshots/2022-StructureTree.png b/uploads/screenshots/2022-StructureTree.png
new file mode 100644
index 0000000000..76b5205431
Binary files /dev/null and b/uploads/screenshots/2022-StructureTree.png differ
diff --git a/uploads/search.png b/uploads/search.png
new file mode 100644
index 0000000000..86ccc39c49
Binary files /dev/null and b/uploads/search.png differ
diff --git a/uploads/setup-webpage-finished.png b/uploads/setup-webpage-finished.png
new file mode 100644
index 0000000000..6888752143
Binary files /dev/null and b/uploads/setup-webpage-finished.png differ
diff --git a/uploads/setup-webpage.png b/uploads/setup-webpage.png
new file mode 100644
index 0000000000..34f6eb8b04
Binary files /dev/null and b/uploads/setup-webpage.png differ
diff --git a/uploads/setup-wizard-gui-jdbc.png b/uploads/setup-wizard-gui-jdbc.png
new file mode 100644
index 0000000000..233ae03694
Binary files /dev/null and b/uploads/setup-wizard-gui-jdbc.png differ
diff --git a/uploads/setup-wizard-step-1.png b/uploads/setup-wizard-step-1.png
new file mode 100644
index 0000000000..07b5539221
Binary files /dev/null and b/uploads/setup-wizard-step-1.png differ
diff --git a/uploads/setup-wizard-step-2.png b/uploads/setup-wizard-step-2.png
new file mode 100644
index 0000000000..fbf3bfabbc
Binary files /dev/null and b/uploads/setup-wizard-step-2.png differ
diff --git a/uploads/slideshow-1/success.1.png b/uploads/slideshow-1/success.1.png
new file mode 100644
index 0000000000..14099f9bf3
Binary files /dev/null and b/uploads/slideshow-1/success.1.png differ
diff --git a/uploads/slideshow-1/success.png b/uploads/slideshow-1/success.png
new file mode 100644
index 0000000000..14099f9bf3
Binary files /dev/null and b/uploads/slideshow-1/success.png differ
diff --git a/uploads/startProjectForge.sh b/uploads/startProjectForge.sh
new file mode 100644
index 0000000000..83b40a351b
--- /dev/null
+++ b/uploads/startProjectForge.sh
@@ -0,0 +1,22 @@
+#!/bin/bash
+
+PF_JAR=${HOME}/application/projectforge-application-xxx.jar"
+
+echo "Using ProjectForge jar: ${PF_JAR}..."
+
+if [ "${OSTYPE}" == 'cygwin' ]
+then
+ JAVA=`cygpath "${JAVA_HOME}"`/jre/bin/java
+else
+ if [[ -n "$JAVA_HOME" ]] && [[ -x "$JAVA_HOME/bin/java" ]]; then
+ JAVA="$JAVA_HOME/bin/java"
+ else
+ JAVA=/usr/bin/java
+ fi
+fi
+
+echo "Using ${JAVA}"
+
+DEBUGOPTS=
+
+nohup ${JAVA} -Xms4g -Xmx4g ${DEBUGOPTS} -jar $PF_JAR 2>&1 > /dev/null &
diff --git a/uploads/stopProjectForge.sh b/uploads/stopProjectForge.sh
new file mode 100755
index 0000000000..b9b9b7e51a
--- /dev/null
+++ b/uploads/stopProjectForge.sh
@@ -0,0 +1,34 @@
+#!/bin/bash
+
+PROCESS_IDENTIFIER="java.*projectforge-application"
+APP_NAME="ProjectForge"
+
+checkStopped() {
+ pid=$(pgrep -f $PROCESS_IDENTIFIER)
+ if [[ -z $pid ]]; then
+ echo "${APP_NAME} $1"
+ exit 0
+ fi
+ if [[ -n $2 ]]; then
+ echo "${APP_NAME} $2"
+ fi
+}
+
+checkStopped "process not found (already terminated?)"
+
+echo "Sending shutdown signal to $APP_NAME..."
+kill $pid
+
+# Loop 20 times a 3 seconds to wait for ProjectForge's shutdown:
+for run in {1..20}; do
+ echo "waiting 3 sec for termination of pid $pid..."
+ sleep 3
+ checkStopped "successfully stopped."
+done
+
+checkStopped "successfully stopped." "not stopped, sending sigkill now..."
+kill -9 $pid
+
+sleep 2
+
+checkStopped "killed." "cannot be killed?!"
diff --git a/uploads/userguide/AddressEdit-Favorites.png b/uploads/userguide/AddressEdit-Favorites.png
new file mode 100644
index 0000000000..b3865bf852
Binary files /dev/null and b/uploads/userguide/AddressEdit-Favorites.png differ
diff --git a/uploads/userguide/AddressList-NumberZoom.png b/uploads/userguide/AddressList-NumberZoom.png
new file mode 100644
index 0000000000..2d234336a7
Binary files /dev/null and b/uploads/userguide/AddressList-NumberZoom.png differ
diff --git a/uploads/userguide/Aufgabe_Kost2.png b/uploads/userguide/Aufgabe_Kost2.png
new file mode 100644
index 0000000000..c7df5fcf21
Binary files /dev/null and b/uploads/userguide/Aufgabe_Kost2.png differ
diff --git a/uploads/userguide/Auftragsbuch-Notification.png b/uploads/userguide/Auftragsbuch-Notification.png
new file mode 100644
index 0000000000..d8ee98a4b7
Binary files /dev/null and b/uploads/userguide/Auftragsbuch-Notification.png differ
diff --git a/uploads/userguide/Bookmark-edit.png b/uploads/userguide/Bookmark-edit.png
new file mode 100644
index 0000000000..03f4008873
Binary files /dev/null and b/uploads/userguide/Bookmark-edit.png differ
diff --git a/uploads/userguide/Bookmark-list.png b/uploads/userguide/Bookmark-list.png
new file mode 100644
index 0000000000..e4c21a1d69
Binary files /dev/null and b/uploads/userguide/Bookmark-list.png differ
diff --git a/uploads/userguide/Consumption-empty.png b/uploads/userguide/Consumption-empty.png
new file mode 100644
index 0000000000..6e19018225
Binary files /dev/null and b/uploads/userguide/Consumption-empty.png differ
diff --git a/uploads/userguide/Consumption-green.png b/uploads/userguide/Consumption-green.png
new file mode 100644
index 0000000000..93d7944fd9
Binary files /dev/null and b/uploads/userguide/Consumption-green.png differ
diff --git a/uploads/userguide/Consumption-orange-red.png b/uploads/userguide/Consumption-orange-red.png
new file mode 100644
index 0000000000..c047ed845c
Binary files /dev/null and b/uploads/userguide/Consumption-orange-red.png differ
diff --git a/uploads/userguide/Consumption-orange.png b/uploads/userguide/Consumption-orange.png
new file mode 100644
index 0000000000..af06d90e8a
Binary files /dev/null and b/uploads/userguide/Consumption-orange.png differ
diff --git a/uploads/userguide/Consumption-red.png b/uploads/userguide/Consumption-red.png
new file mode 100644
index 0000000000..1c50a93d06
Binary files /dev/null and b/uploads/userguide/Consumption-red.png differ
diff --git a/uploads/userguide/Consumption-yellow.png b/uploads/userguide/Consumption-yellow.png
new file mode 100644
index 0000000000..be9839559d
Binary files /dev/null and b/uploads/userguide/Consumption-yellow.png differ
diff --git a/uploads/userguide/Datev-Import-Buchungssaetze.png b/uploads/userguide/Datev-Import-Buchungssaetze.png
new file mode 100644
index 0000000000..411bd7c9db
Binary files /dev/null and b/uploads/userguide/Datev-Import-Buchungssaetze.png differ
diff --git a/uploads/userguide/Datev-Import-Kontenplan.png b/uploads/userguide/Datev-Import-Kontenplan.png
new file mode 100644
index 0000000000..7012f6c2b2
Binary files /dev/null and b/uploads/userguide/Datev-Import-Kontenplan.png differ
diff --git a/uploads/userguide/Datev-Import-step1.png b/uploads/userguide/Datev-Import-step1.png
new file mode 100644
index 0000000000..c2f37c91b4
Binary files /dev/null and b/uploads/userguide/Datev-Import-step1.png differ
diff --git a/uploads/userguide/Datev-Import-step2.png b/uploads/userguide/Datev-Import-step2.png
new file mode 100644
index 0000000000..e8acb3249b
Binary files /dev/null and b/uploads/userguide/Datev-Import-step2.png differ
diff --git a/uploads/userguide/Datev-Import-step3.png b/uploads/userguide/Datev-Import-step3.png
new file mode 100644
index 0000000000..5d1140f631
Binary files /dev/null and b/uploads/userguide/Datev-Import-step3.png differ
diff --git a/uploads/userguide/Datev-Import-step4.png b/uploads/userguide/Datev-Import-step4.png
new file mode 100644
index 0000000000..477850c957
Binary files /dev/null and b/uploads/userguide/Datev-Import-step4.png differ
diff --git a/uploads/userguide/Datev-Import-step5.png b/uploads/userguide/Datev-Import-step5.png
new file mode 100644
index 0000000000..3623573732
Binary files /dev/null and b/uploads/userguide/Datev-Import-step5.png differ
diff --git a/uploads/userguide/Direktwahl-Adressbuch.png b/uploads/userguide/Direktwahl-Adressbuch.png
new file mode 100644
index 0000000000..1c44d3c1c5
Binary files /dev/null and b/uploads/userguide/Direktwahl-Adressbuch.png differ
diff --git a/uploads/userguide/Direktwahl.png b/uploads/userguide/Direktwahl.png
new file mode 100644
index 0000000000..34de17f1e3
Binary files /dev/null and b/uploads/userguide/Direktwahl.png differ
diff --git a/uploads/userguide/Excel-import-example.png b/uploads/userguide/Excel-import-example.png
new file mode 100644
index 0000000000..57dba51ece
Binary files /dev/null and b/uploads/userguide/Excel-import-example.png differ
diff --git a/uploads/userguide/ExportJFreeChart.png b/uploads/userguide/ExportJFreeChart.png
new file mode 100644
index 0000000000..d50aa3cd7e
Binary files /dev/null and b/uploads/userguide/ExportJFreeChart.png differ
diff --git a/uploads/userguide/PF-TeamCal-Access-preview.png b/uploads/userguide/PF-TeamCal-Access-preview.png
new file mode 100644
index 0000000000..f370a55ae6
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-Access-preview.png differ
diff --git a/uploads/userguide/PF-TeamCal-Access.png b/uploads/userguide/PF-TeamCal-Access.png
new file mode 100644
index 0000000000..a4fa53f658
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-Access.png differ
diff --git a/uploads/userguide/PF-TeamCal-MonthView-preview.png b/uploads/userguide/PF-TeamCal-MonthView-preview.png
new file mode 100644
index 0000000000..d1294ff67a
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-MonthView-preview.png differ
diff --git a/uploads/userguide/PF-TeamCal-MonthView.png b/uploads/userguide/PF-TeamCal-MonthView.png
new file mode 100644
index 0000000000..c251f64985
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-MonthView.png differ
diff --git a/uploads/userguide/PF-TeamCal-RecurrenceDialog-preview.png b/uploads/userguide/PF-TeamCal-RecurrenceDialog-preview.png
new file mode 100644
index 0000000000..7367096485
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-RecurrenceDialog-preview.png differ
diff --git a/uploads/userguide/PF-TeamCal-RecurrenceDialog.png b/uploads/userguide/PF-TeamCal-RecurrenceDialog.png
new file mode 100644
index 0000000000..fa641ce293
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-RecurrenceDialog.png differ
diff --git a/uploads/userguide/PF-TeamCal-Subscription-preview.png b/uploads/userguide/PF-TeamCal-Subscription-preview.png
new file mode 100644
index 0000000000..8c27450e5c
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-Subscription-preview.png differ
diff --git a/uploads/userguide/PF-TeamCal-Subscription.png b/uploads/userguide/PF-TeamCal-Subscription.png
new file mode 100644
index 0000000000..64bb7e3fff
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-Subscription.png differ
diff --git a/uploads/userguide/PF-TeamCal-Weekview-preview.png b/uploads/userguide/PF-TeamCal-Weekview-preview.png
new file mode 100644
index 0000000000..0909de9bd0
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-Weekview-preview.png differ
diff --git a/uploads/userguide/PF-TeamCal-Weekview.png b/uploads/userguide/PF-TeamCal-Weekview.png
new file mode 100644
index 0000000000..00c7ca98a3
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-Weekview.png differ
diff --git a/uploads/userguide/PF-TeamCal-filters-preview.png b/uploads/userguide/PF-TeamCal-filters-preview.png
new file mode 100644
index 0000000000..31599dd86f
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-filters-preview.png differ
diff --git a/uploads/userguide/PF-TeamCal-filters.png b/uploads/userguide/PF-TeamCal-filters.png
new file mode 100644
index 0000000000..c61d65bdb5
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-filters.png differ
diff --git a/uploads/userguide/PF-TeamCal-ical-preview.png b/uploads/userguide/PF-TeamCal-ical-preview.png
new file mode 100644
index 0000000000..7507855080
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-ical-preview.png differ
diff --git a/uploads/userguide/PF-TeamCal-ical.png b/uploads/userguide/PF-TeamCal-ical.png
new file mode 100644
index 0000000000..cb9bd16a0e
Binary files /dev/null and b/uploads/userguide/PF-TeamCal-ical.png differ
diff --git a/uploads/userguide/PF-liquidity.png b/uploads/userguide/PF-liquidity.png
new file mode 100644
index 0000000000..1b974c3a24
Binary files /dev/null and b/uploads/userguide/PF-liquidity.png differ
diff --git a/uploads/userguide/TaskTree.png b/uploads/userguide/TaskTree.png
new file mode 100644
index 0000000000..1ec882866e
Binary files /dev/null and b/uploads/userguide/TaskTree.png differ
diff --git a/uploads/userguide/Zeitbericht_anlegen_kost2.png b/uploads/userguide/Zeitbericht_anlegen_kost2.png
new file mode 100644
index 0000000000..2287124780
Binary files /dev/null and b/uploads/userguide/Zeitbericht_anlegen_kost2.png differ
diff --git a/uploads/userguide/Zeitberichtsschutz.png b/uploads/userguide/Zeitberichtsschutz.png
new file mode 100644
index 0000000000..30203d4505
Binary files /dev/null and b/uploads/userguide/Zeitberichtsschutz.png differ
diff --git a/uploads/userguide/Zeitblaettern.png b/uploads/userguide/Zeitblaettern.png
new file mode 100644
index 0000000000..3c214d3383
Binary files /dev/null and b/uploads/userguide/Zeitblaettern.png differ
diff --git a/uploads/userguide/extendedFilter.png b/uploads/userguide/extendedFilter.png
new file mode 100644
index 0000000000..bb753dab7d
Binary files /dev/null and b/uploads/userguide/extendedFilter.png differ
diff --git a/uploads/userguide/searchfield.png b/uploads/userguide/searchfield.png
new file mode 100644
index 0000000000..bb4e82a2c4
Binary files /dev/null and b/uploads/userguide/searchfield.png differ
diff --git a/welcome-to-jekyll/index.html b/welcome-to-jekyll/index.html
new file mode 100644
index 0000000000..f539ff6651
--- /dev/null
+++ b/welcome-to-jekyll/index.html
@@ -0,0 +1,563 @@
+
+
+
+
+
+
+
+
+
Welcome to Jekyll! | ProjectForge
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
Docs
+
+
+
+
+
+
+
+
+
+ Home
+
+
+
+
+
+
+
+
+
+ GitHub
+
+
+
+
+
+
+
+
+
+ Features
+
+
+
+
+
+
+
+
+
+ Docs
+
+
+
+
+
+
+
+
+
+
+
+
+
+ FAQ
+
+
+
+
+
+
+
+
+
+ About
+
+
+
+
+
+
+
+
+
+ Search
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
Menu
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ Welcome to Jekyll!
+
+
+
+
+
+
+
+
+
+
+
+ Written by Kai Reinhard
+
+
+
+ Aug 9, 2021
+
+
+
+
+
+
+
You’ll find this post in your _posts
directory. Go ahead and edit it and re-build the site to see your changes. You can rebuild the site in many different ways, but the most common way is to run jekyll serve
, which launches a web server and auto-regenerates your site when a file is updated.
+
+
+
Jekyll requires blog post files to be named according to the following format:
+
+
+
YEAR-MONTH-DAY-title.MARKUP
+
+
+
Where YEAR
is a four-digit number, MONTH
and DAY
are both two-digit numbers, and MARKUP
is the file extension representing the format used in the file. After that, include the necessary front matter. Take a look at the source for this post to get an idea about how it works.
+
+
+
Jekyll also offers powerful support for code snippets:
+
+
+
{% highlight ruby %}
+def print_hi(name)
+ puts "Hi, #{name}"
+end
+print_hi('Tom')
+#⇒ prints 'Hi, Tom' to STDOUT.
+{% endhighlight %}
+
+
+
Check out the [Jekyll docs][jekyll-docs] for more info on how to get the most out of Jekyll. File all bugs/feature requests at [Jekyll’s GitHub repo][jekyll-gh]. If you have questions, you can ask them on [Jekyll Talk][jekyll-talk].
+
+
+
+
+
+
+
+
+
+
+
+
Related Posts
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
Documentation
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
ProjectForge© is a registered trade mark.
+
+
+
+
+
+
+
+
+
+
+
+
+