# HG changeset patch # User Drew Perttula # Date 2018-05-18 07:54:42 # Node ID 7cb53b510a6a5377bcc22aa3e899afb64dfea434 # Parent 7e66643b3f5483085c6ecefa1d5976642aae3a8b draw notes, colors. position adjusters better. Ignore-this: 1ccdb7109cfa67cc0486d9418b42be4e diff --git a/light9/web/timeline/adjustable.coffee b/light9/web/timeline/adjustable.coffee --- a/light9/web/timeline/adjustable.coffee +++ b/light9/web/timeline/adjustable.coffee @@ -110,7 +110,7 @@ class window.AdjustableFloatObject exten @ctor2() if not @config.ctx? throw new Error("missing ctx") - @config.graph.runHandler(@_syncValue.bind(@), "adj sync #{@config.subj}") + @config.graph.runHandler(@_syncValue.bind(@), "adj sync #{@config.subj.value}") _syncValue: () -> @_currentValue = @config.graph.floatValue(@config.subj, @config.pred) diff --git a/light9/web/timeline/timeline-elements.html b/light9/web/timeline/timeline-elements.html --- a/light9/web/timeline/timeline-elements.html +++ b/light9/web/timeline/timeline-elements.html @@ -68,13 +68,11 @@ graph="{{graph}}" project="{{project}}" selection="{{selection}}" - dia="{{dia}}" set-adjuster="{{setAdjuster}}" song="{{song}}" show="{{show}}" view-state="{{viewState}}"> - @@ -272,6 +270,7 @@ + diff --git a/light9/web/timeline/timeline.coffee b/light9/web/timeline/timeline.coffee --- a/light9/web/timeline/timeline.coffee +++ b/light9/web/timeline/timeline.coffee @@ -150,6 +150,8 @@ coffeeElementSetup(class TimelineEditor _onIronResize: -> @viewState.setWidth(@offsetWidth) + @viewState.coveredByDiagramTop(@$.coveredByDiagram.offsetTop) + @viewState.rowsY(@$.zoomed.$.rows.offsetTop) if @$.zoomed?.$?.rows? @viewState.audioY(@$.audio.offsetTop) @viewState.audioH(@$.audio.offsetHeight) if @$.zoomed?.$?.time? @@ -285,54 +287,57 @@ coffeeElementSetup(class TimeZoomed exte graph: { type: Object, notify: true } project: { type: Object } selection: { type: Object, notify: true } - dia: { type: Object, notify: true } song: { type: String, notify: true } viewState: { type: Object, notify: true } @getter_observers: [ - 'onGraph(graph, setAdjuster, song, viewState, project)', - 'onZoom(viewState)', + '_onGraph(graph, setAdjuster, song, viewState, project)', ] constructor: -> super() + @notes = [] @stage = new PIXI.Container() @renderer = PIXI.autoDetectRenderer({ backgroundColor: 0x606060, + antialias: true, + forceCanvas: true, }) ready: -> super.ready() - @addEventListener('iron-resize', @update.bind(@)) - Polymer.RenderStatus.afterNextRender(this, @update.bind(@)) + @addEventListener('iron-resize', @_onResize.bind(@)) + Polymer.RenderStatus.afterNextRender(this, @_onResize.bind(@)) @$.rows.appendChild(@renderer.view); - - update: -> + + ko.computed => + @stage.setTransform(0, -(@viewState.rowsY()), 1, 1, 0, 0, 0, 0, 0) + + _onResize: -> @renderer.resize(@clientWidth, @clientHeight) @renderer.render(@stage) - - onZoom: -> - updateZoomFlattened = -> - log('updateZoomFlattened') - @zoomFlattened = ko.toJS(@viewState.zoomSpec) - ko.computed(updateZoomFlattened.bind(@)) - onGraph: -> + _onGraph: -> @graph.runHandler(@gatherNotes.bind(@), 'zoom notes') - # not working- worked around in zoomOrLayoutChanged - #ko.computed(@gatherNotes.bind(@)) gatherNotes: -> U = (x) => @graph.Uri(x) - log('assign rows',@song, 'graph has', @graph.quads().length) + log('assign rows',@song) - @stage.children.splice(0) + @stage.removeChildren() + n.destroy() for n in @notes + @notes = [] + noteNum = 0 - for uri in _.sortBy(@graph.objects(@song, U(':note')), 'uri') - note = new Note(@project, @graph, @selection, uri, @setAdjuster, @song, @viewState, @stage, @offsetTop + 150 * (noteNum % 4)) - note.draw() + for uri in _.sortBy(@graph.objects(@song, U(':note')), 'id') + con = new PIXI.Container() + @stage.addChild(con) + row = noteNum % 6 + rowTop = @viewState.rowsY() + 20 + 150 * row + note = new Note(con, @project, @graph, @selection, uri, @setAdjuster, @song, @viewState, rowTop, rowTop + 140) + @notes.push(note) noteNum = noteNum + 1 @renderer.render(@stage) @@ -377,12 +382,12 @@ coffeeElementSetup(class TimeAxis extend # Maintains a pixi object and some adjusters corresponding to a note # in the graph. class Note - constructor: (@project, @graph, @selection, @uri, @setAdjuster, @song, @viewState, @stage, @rowTopY) -> + constructor: (@container, @project, @graph, @selection, @uri, @setAdjuster, @song, @viewState, @rowTopY, @rowBotY) -> @adjusterIds = {} # id : true + @draw() destroy: -> - log('destroy', @uri) - # pixi rm + log('destroy', @uri.value) @isDetached = true @clearAdjusters() @@ -390,32 +395,42 @@ class Note for i in Object.keys(@adjusterIds) @setAdjuster(i, null) + getCurvePoints: (subj, curveAttr) -> + U = (x) => @graph.Uri(x) + originTime = @graph.floatValue(subj, U(':originTime')) + + for curve in @graph.objects(subj, U(':curve')) + if @graph.uriValue(curve, U(':attr')).equals(curveAttr) + + return @project.getCurvePoints(curve, originTime) + throw new Error("curve #{@uri.value} has no attr #{curveAttr.value}") + draw: -> U = (x) => @graph.Uri(x) - originTime = @graph.floatValue(@uri, U(':originTime')) + [pointUris, worldPts] = @getCurvePoints(@uri, U(':strength')) effect = @graph.uriValue(@uri, U(':effectClass')) - graphics = new PIXI.Graphics({nativeLines: true}) + + yForV = (v) => @rowBotY + (@rowTopY - @rowBotY) * v + dependOn = [@viewState.zoomSpec.t1(), @viewState.zoomSpec.t2(), @viewState.width()] + screenPts = (new PIXI.Point(@viewState.zoomInX(pt.e(1)), yForV(pt.e(2))) for pt in worldPts) - for curve in @graph.objects(@uri, U(':curve')) - if @graph.uriValue(curve, U(':attr')).equals(U(':strength')) - - [pointUris, worldPts] = @project.getCurvePoints(curve, originTime) - curveWidthCalc = () => @project.curveWidth(worldPts) + @container.removeChildren() + graphics = new PIXI.Graphics({nativeLines: false}) + @container.addChild(graphics) - h = 150 #@offsetHeight - yForV = (v) => @rowTopY + (1 - v) * h - dependOn = [@viewState.zoomSpec.t1(), @viewState.zoomSpec.t2(), @viewState.width()] - screenPts = ($V([@viewState.zoomInX(pt.e(1)), yForV(pt.e(2))]) for pt in worldPts) - graphics.beginFill(0xFF3300) - graphics.lineStyle(4, 0xffd900, 1) + shape = new PIXI.Polygon(screenPts) + graphics.beginFill(@_noteColor(effect), .313) + graphics.drawShape(shape) + graphics.endFill() - graphics.moveTo(screenPts[0].e(1), screenPts[0].e(2)) - for p in screenPts.slice(1) - graphics.lineTo(p.e(1), p.e(2)) - graphics.endFill() - @_updateAdjusters(screenPts, worldPts, curveWidthCalc, yForV, @song) - @_updateInlineAttrs(screenPts) - @stage.addChild(graphics) + graphics.lineStyle(2, 0xffd900, 1) + graphics.moveTo(screenPts[0].x, screenPts[0].y) + for p in screenPts.slice(1) + graphics.lineTo(p.x, p.y) + + curveWidthCalc = () => @project.curveWidth(worldPts) + @_updateAdjusters(screenPts, worldPts, curveWidthCalc, yForV, @song) + @_updateInlineAttrs(screenPts) onUri: -> @graph.runHandler(@update.bind(@), "note updates #{@uri}") @@ -445,16 +460,16 @@ class Note @_updateDisplay() _updateAdjusters: (screenPts, worldPts, curveWidthCalc, yForV, ctx) -> - if screenPts[screenPts.length - 1].e(1) - screenPts[0].e(1) < 100 + if screenPts[screenPts.length - 1].x - screenPts[0].x < 100 @clearAdjusters() else @_makeOffsetAdjuster(yForV, curveWidthCalc, ctx) @_makeCurvePointAdjusters(yForV, worldPts, ctx) - #@_makeFadeAdjusters(yForV, ctx) + @_makeFadeAdjusters(yForV, ctx, worldPts) _updateInlineAttrs: (screenPts) -> - leftX = Math.max(2, screenPts[Math.min(1, screenPts.length - 1)].e(1) + 5) - rightX = screenPts[Math.min(2, screenPts.length - 1)].e(1) - 5 + leftX = Math.max(2, screenPts[Math.min(1, screenPts.length - 1)].x + 5) + rightX = screenPts[Math.min(2, screenPts.length - 1)].x - 5 if screenPts.length < 3 rightX = leftX + 120 w = 250 @@ -478,7 +493,7 @@ class Note _makePointAdjuster: (yForV, worldPts, pointNum, ctx) -> U = (x) => @graph.Uri(x) - adjId = @uri + '/p' + pointNum + adjId = @uri.value + '/p' + pointNum @adjusterIds[adjId] = true @setAdjuster adjId, => adj = new AdjustableFloatObject({ @@ -503,7 +518,7 @@ class Note _makeOffsetAdjuster: (yForV, curveWidthCalc, ctx) -> U = (x) => @graph.Uri(x) - adjId = @uri + '/offset' + adjId = @uri.value + '/offset' @adjusterIds[adjId] = true @setAdjuster adjId, => adj = new AdjustableFloatObject({ @@ -521,12 +536,14 @@ class Note }) adj - _makeFadeAdjusters: (yForV, ctx) -> - @_makeFadeAdjuster(yForV, ctx, @uri + '/fadeIn', 0, 1, $V([-50, -10])) - n = @worldPts.length - @_makeFadeAdjuster(yForV, ctx, @uri + '/fadeOut', n - 2, n - 1, $V([50, -10])) + _makeFadeAdjusters: (yForV, ctx, worldPts) -> + U = (x) => @graph.Uri(x) + @_makeFadeAdjuster(yForV, ctx, @uri.value + '/fadeIn', 0, 1, $V([-50, -10])) + n = worldPts.length + @_makeFadeAdjuster(yForV, ctx, @uri.value + '/fadeOut', n - 2, n - 1, $V([50, -10])) _makeFadeAdjuster: (yForV, ctx, adjId, i0, i1, offset) -> + return # not ready- AdjustableFade looks in Note object @adjusterIds[adjId] = true @setAdjuster adjId, => new AdjustableFade(yForV, i0, i1, @, offset, ctx) @@ -554,7 +571,8 @@ class Note elem.addEventListener 'mouseleave', => @selection.hover(null) - _noteAttrs: (effect) -> + _noteColor: (effect) -> + effect = effect.value if effect in ['http://light9.bigasterisk.com/effect/blacklight', 'http://light9.bigasterisk.com/effect/strobewarm'] hue = 0 @@ -566,10 +584,10 @@ class Note hue = (hash * 8) % 360 sat = 40 + (hash % 20) # don't conceal colorscale too much - {style: "fill:hsla(#{hue}, #{sat}%, 58%, 0.313);"} + return parseInt(tinycolor.fromRatio({h: hue / 360, s: sat / 100, l: .58}).toHex(), 16) _noteInDiagram: (uri) -> - return !!@elemById[uri + '/area'] + return !!@elemById[uri.value + '/area'] _updateNotePathClasses: (uri, elem) -> ko.computed => diff --git a/light9/web/timeline/viewstate.coffee b/light9/web/timeline/viewstate.coffee --- a/light9/web/timeline/viewstate.coffee +++ b/light9/web/timeline/viewstate.coffee @@ -10,10 +10,13 @@ class window.ViewState @mouse = pos: ko.observable($V([0,0])) @width = ko.observable(500) + @coveredByDiagramTop = ko.observable(0) # page coords + # all these are relative to #coveredByDiagram: @audioY = ko.observable(0) @audioH = ko.observable(0) @zoomedTimeY = ko.observable(0) @zoomedTimeH = ko.observable(0) + @rowsY = ko.observable(0) @fullZoomX = d3.scaleLinear() @zoomInX = d3.scaleLinear() diff --git a/package.json b/package.json --- a/package.json +++ b/package.json @@ -18,7 +18,8 @@ "d3": "^5.1.0", "mocha": "^2.5.3", "n3": "^1.0.0-alpha", - "pixi.js": "^4.7.3" + "pixi.js": "^4.7.3", + "tinycolor2": "^1.4.1" }, "devDependencies": { "mocha": "^2.5.3"