Compare commits

..

No commits in common. "Astro" and "master" have entirely different histories.

360 changed files with 542 additions and 28648 deletions

View File

@ -1,17 +0,0 @@
.dockerignore
.git
.gitignore
*~
*.swp
*.pyc
Dockerfile
k8s/
cache/
image/
concourse/
k8s/
windows/
__pycache__
cache/*
logs/*
env/*

1
.gitignore vendored
View File

@ -1,4 +1,3 @@
.DS_Store
*~ *~
*.swp *.swp
*.pyc *.pyc

View File

@ -1,24 +0,0 @@
FROM alpine:3.15.3
WORKDIR /app
RUN mkdir -p /opt/utils
RUN apk add --update bash python3 uwsgi uwsgi-python openjdk11-jre-headless; python3 -m ensurepip
RUN echo "www-data:x:1001:1001:www-data:/var/www:/usr/sbin/nologin" >> /etc/passwd; echo "www-data:x:1001:" >> /etc/group
RUN pip3 install Flask redis compressinja Celery
ADD [ "https://github.com/tgckpg/BotanJS/releases/download/compressors/closure.jar" \
, "https://github.com/tgckpg/BotanJS/releases/download/compressors/yuicompressor.jar" \
, "/opt/utils/" ]
COPY . /app/
RUN chmod 644 /opt/utils/*.jar; \
chown www-data:www-data . -R
USER www-data
EXPOSE 5000
ENTRYPOINT ["setup/docker.start"]

View File

@ -1,11 +1,8 @@
# AstroJS for Blog # BotanJS
[![Image](https://build.s.k8s.astropenguin.net/api/v1/teams/main/pipelines/astrojs/badge)](https://build.s.k8s.astropenguin.net/teams/main/pipelines/astrojs) A working concept of Js/Css framework for web browsers
The current backend Js/Css services for [my blog](https://blog.astropenguin.net) ### Showcase
- Pending
### Try it - Docker for windows (using windows container with nanoserver)
- docker -f windows/docker-compose.yml build
- docker -f windows/docker-compose.yml up
### Features ### Features
- Compressable by Closure Compiler (Advanced Compression) - Compressable by Closure Compiler (Advanced Compression)
@ -13,13 +10,29 @@ The current backend Js/Css services for [my blog](https://blog.astropenguin.net)
- Everything is merged into one file for that page - Everything is merged into one file for that page
- css class inheritance - css class inheritance
### Disclaimer
- This is a working concept. So it works on me. And may have a bunch of useless dependency. Use at your own risks!
### Documentation ### Documentation
- Will be added later - Will be added later
### Prerequisties ### Prerequisties
- python3 - python3
- virtualenv ( optional ) - virtualenv
#### For Service.WebAPI
- pip install Flask - pip install Flask
- pip install Celery - pip install Celery
- pip install redis - pip install redis
- pip install compressinja - pip install compressinja
### Before start, run
```
virtualenv env
./botan-rebuild
```
#### To start just run ( in virtualenv )
```
./botan-start
```

View File

@ -1,4 +1,4 @@
#!/usr/bin/env python3 #!env/bin/python
import os, sys import os, sys
sys.path.append( os.path.abspath( "." ) ) sys.path.append( os.path.abspath( "." ) )
@ -8,10 +8,10 @@ from botanjs.config import Config as config
SiteRoot = os.path.abspath( "." ) SiteRoot = os.path.abspath( "." )
# Setting the SiteRoot for config # Setting the SiteRoot for config
config["Paths"]["SiteRoot"] = SiteRoot config["Paths"]["SiteRoot"] = SiteRoot;
bmap = os.path.join( config["Paths"]["Cache"], "botanjs", "bmap.xml" ) bmap = os.path.join( config["Paths"]["Cache"], "botanjs", "bmap.xml" )
app.conf.update( broker_url = config["BotanJS"]["CeleryBroker"] ) app.conf.update( BROKER_URL = config["BotanJS"]["CeleryBroker"] )
JWork.buildClassMap.delay( config["BotanJS"]["SrcDir"], bmap ) JWork.buildClassMap.delay( config["BotanJS"]["SrcDir"], bmap )

57
botan-start.py Executable file
View File

@ -0,0 +1,57 @@
#!env/bin/python
import os, sys
from botanjs.config import Config as config, DEBUG
from subprocess import Popen
from botanjs.service.webapi import WebAPI
SiteRoot = os.path.abspath( "." )
# Setting the SiteRoot for config
config["Paths"]["SiteRoot"] = SiteRoot;
# Create the lock folder for celery
lockDir = os.path.join( SiteRoot, "env", "var", "run", "celery" )
os.makedirs( lockDir, exist_ok=True )
sys.path.append( os.path.abspath( "." ) )
RUNTIME_ENV = os.path.abspath( os.path.join( "env", "bin" ) )
if RUNTIME_ENV not in os.environ[ "PATH" ]:
os.environ[ "PATH" ] = RUNTIME_ENV + os.pathsep + os.environ[ "PATH" ]
if __name__ == "__main__":
jwork = "botanjs.service.jwork"
nodeName = "botanNode1"
celOut = open( os.path.join( config["Paths"]["Log"], jwork + "-err.log" ), "a+" )
cel = Popen(
[
"celery", "multi", "restart", nodeName
, "-A", jwork, "worker"
, "--pidfile=" + os.path.join( lockDir, jwork + ".pid" )
, "--logfile=" + os.path.join( config["Paths"]["Log"], jwork + ".log" )
, "--workdir=" + config["Paths"]["Runtime"]
, "beat", "-l", "info"
]
, stdout = celOut
, stderr = celOut
)
celOut.close()
if not DEBUG and os.fork():
import logging
logging.basicConfig(
filename = os.path.join( config["Paths"]["Log"], "access.log" )
, level = logging.DEBUG
)
sys.exit()
WebAPI(
jsCache = config["Paths"]["Cache"]
, jsRoot = config["BotanJS"]["SrcDir"]
, brokerURL = config["BotanJS"]["CeleryBroker"]
)

View File

@ -1,15 +1,12 @@
import os, re, sys #!/usr/bin/env python3
import os;
import re;
import sys;
from xml.dom import minidom from xml.dom import minidom
from collections import defaultdict from collections import defaultdict
from botanjs.config import DEBUG
if DEBUG:
from botanjs.utils import checksum_r as checksum
else:
from botanjs.utils import checksum
RegEx_N = re.compile( r""" RegEx_N = re.compile( r"""
.* .*
__namespace __namespace
@ -139,7 +136,7 @@ class ClassMap:
return True; return True;
def drawMap( self, ns, ci, ce, cf, chksum ): def drawMap( self, ns, ci, ce, cf ):
nsNode = self.getNode( ns ) nsNode = self.getNode( ns )
# Source every: # Source every:
@ -153,8 +150,6 @@ class ClassMap:
if not srcEvery: if not srcEvery:
nsNode.setAttribute( "src", cf ) nsNode.setAttribute( "src", cf )
nsNode.setAttribute( "js", chksum["js"] )
nsNode.setAttribute( "css", chksum["css"] )
for ex in ce: for ex in ce:
_t = eDef[ ex[0] ] _t = eDef[ ex[0] ]
@ -169,8 +164,6 @@ class ClassMap:
cNode.appendChild( impNode ) cNode.appendChild( impNode )
cNode.setAttribute( "src", cf ) cNode.setAttribute( "src", cf )
cNode.setAttribute( "js", chksum["js"] )
cNode.setAttribute( "css", chksum["css"] )
# the file dose not export classes # the file dose not export classes
# Hence it import for itself # Hence it import for itself
@ -194,11 +187,7 @@ class ClassMap:
continue continue
ns, ci, ce = classMeta( classFile ) ns, ci, ce = classMeta( classFile )
chksum = {}
chksum[ "js" ] = checksum( classFile )
chksum[ "css" ] = checksum( classFile[:-2] + "css" )
classFile = classFile.replace( self.R + os.path.sep, "" ) classFile = classFile.replace( self.R + os.path.sep, "" )
self.drawMap( ns, ci, ce, classFile, chksum ) self.drawMap( ns, ci, ce, classFile )
return self.DOM.toxml() return self.DOM.toxml()

16
botanjs/compressor/closure.py Normal file → Executable file
View File

@ -1,14 +1,13 @@
#!/usr/bin/env python3 #!/usr/bin/env python3
import os import os
from sys import platform
from tempfile import NamedTemporaryFile from tempfile import NamedTemporaryFile
from botanjs.config import Config as config from botanjs.config import Config as config
from botanjs.service.jwork import log
COMPILER = config[ "BotanJS" ][ "ClosureCompiler" ] COMPILER = config[ "BotanJS" ][ "ClosureCompiler" ]
AVAILABLE = os.path.isfile( COMPILER ) if not os.path.isfile( COMPILER ):
raise Exception( "Compiler not found" )
COMPILER_OPTIONS = [ COMPILER_OPTIONS = [
@ -24,7 +23,7 @@ class Wrapper:
E = "" E = ""
def __init__( self ): def __init__( self ):
self.C = "java -jar -Xmx64M "+ COMPILER + " " + " ".join( COMPILER_OPTIONS ) self.C = "java -jar "+ COMPILER + " " + " ".join( COMPILER_OPTIONS )
def scanExterns( self, sdir ): def scanExterns( self, sdir ):
for root, dirs, files in os.walk( sdir ): for root, dirs, files in os.walk( sdir ):
@ -42,15 +41,12 @@ class Wrapper:
break break
def compress( self, loc ): def compress( self, loc ):
if not AVAILABLE:
log.error( "Compiler not found" )
return
content = "" content = ""
with open( loc, "rb" ) as f: with open( loc, "rb" ) as f:
content = f.read() content = f.read()
with NamedTemporaryFile( delete = ( not platform == "win32" ) ) as f: with NamedTemporaryFile() as f:
f.write( content[12:-5] ) f.write( content[12:-5] )
os.system( self.C + self.E + " --js " + f.name + " --js_output_file " + loc[:-3] + ".c.js" ) os.system( self.C + self.E + " --js " + f.name + " --js_output_file " + loc[:-3] + ".c.js" )

6
botanjs/compressor/yui.py Normal file → Executable file
View File

@ -1,7 +1,6 @@
#!/usr/bin/env python3 #!/usr/bin/env python3
import os import os
from sys import platform
from botanjs.config import Config as config from botanjs.config import Config as config
COMPILER = config[ "BotanJS" ][ "YuiCompressor" ] COMPILER = config[ "BotanJS" ][ "YuiCompressor" ]
@ -21,8 +20,5 @@ class Wrapper:
self.C = "java -jar " + COMPILER + " " + " ".join( COMPILER_OPTIONS ) self.C = "java -jar " + COMPILER + " " + " ".join( COMPILER_OPTIONS )
def compress( self, loc ): def compress( self, loc ):
if platform == "win32":
loc = loc.replace( "C:", "" ).replace( "\\\\", "/" )
os.system( self.C + " " + loc + " -o " + loc[:-4] + ".c.css" ) os.system( self.C + " " + loc + " -o " + loc[:-4] + ".c.css" )

12
botanjs/config.py Normal file → Executable file
View File

@ -1,15 +1,7 @@
#!/usr/bin/env python3 #!/usr/bin/env python3
import configparser, os import configparser
Config = configparser.ConfigParser( interpolation = configparser.ExtendedInterpolation() ) Config = configparser.ConfigParser( interpolation = configparser.ExtendedInterpolation() )
Config.read( "settings.ini" ) Config.read( "settings.ini" )
DEBUG = os.getenv( "DEBUG" ) DEBUG = Config[ "Env" ][ "Debug" ]
if DEBUG is None:
DEBUG = Config.getboolean( "Env", "Debug" )
else:
Config[ "Env" ][ "Debug" ] = str( DEBUG == "1" )
REDIS_CONN = os.getenv( "REDIS_CONN" )
if not REDIS_CONN is None:
Config[ "Redis" ][ "ConnStr" ] = REDIS_CONN

View File

@ -1,13 +1,7 @@
#!/usr/bin/env python3 #!/usr/bin/env python3
class log: class log:
def info( self, *args ):
@staticmethod
def info( *args ):
print( *args )
@staticmethod
def error( *args ):
print( *args ) print( *args )
class dummyTask( object ): class dummyTask( object ):
@ -24,7 +18,7 @@ class dummyTask( object ):
pass pass
class dummyConf: class dummyConf:
def update( self, broker_url = None ): def update( self, BROKER_URL = None ):
pass pass
class app: class app:

View File

@ -16,11 +16,8 @@ class Resolver:
EX_FUNC = "method" EX_FUNC = "method"
EX_CLASS = "class" EX_CLASS = "class"
_rLookup = None
def __init__( self, classMap ): def __init__( self, classMap ):
self.classMap = classMap self.classMap = classMap
self._rLookup = {}
self._reload() self._reload()
def _reload( self ): def _reload( self ):
@ -33,23 +30,13 @@ class Resolver:
def resource( self, elem ): def resource( self, elem ):
if "src" in elem.attrib: if "src" in elem.attrib:
key = elem.attrib[ "src" ] return elem.attrib[ "src" ]
if not key in self._rLookup:
self._rLookup[ key ] = {
"src": elem.attrib[ "src" ]
, "js": elem.attrib[ "js" ]
, "css": elem.attrib[ "css" ]
}
return self._rLookup[ key ]
parent = self.parentMap[ elem ] parent = self.parentMap[ elem ]
if parent is not None: if parent != None:
return self.resource( parent ) return self.resource( parent )
def locate( self, key ):
return self._rLookup.get( key )
def resolve( self, c, classList ): def resolve( self, c, classList ):
self.resolved = [] self.resolved = []
self.__resolve( c, classList ) self.__resolve( c, classList )
@ -112,9 +99,7 @@ class BotanClassResolver:
classMap = "" classMap = ""
flagCompress = True flagCompress = True
oModeIfSizelt = 50 * 1024
returnHash = False returnHash = False
returnDynamic = False
resv = None resv = None
def __init__( self, jwork, BotanRoot, classMap, cacheRoot ): def __init__( self, jwork, BotanRoot, classMap, cacheRoot ):
@ -137,17 +122,12 @@ class BotanClassResolver:
return content return content
def BotanCache( self, srcFile, fileHash, hashContentDynamic ): def BotanCache( self, t ):
content = ""
with open( t, "r" ) as f:
content = f.read()
for _ in [0]: return content
if hashContentDynamic and os.path.getsize( srcFile ) < self.oModeIfSizelt:
break
if self.returnHash:
return fileHash
with open( srcFile, "r" ) as f:
return f.read()
def cleanList( self, lista ): def cleanList( self, lista ):
olist = [] olist = []
@ -166,35 +146,37 @@ class BotanClassResolver:
if src not in classFiles: if src not in classFiles:
classFiles.append( src ) classFiles.append( src )
def cssLookup( self, classList, cssList ): def cssLookup( self, jsList, cssList ):
for cdef in classList: for f in jsList:
f = cdef[ "src" ] possibleList = []
cssFile = os.path.splitext( f )[0] + ".css" cssFile = os.path.splitext( f )[0] + ".css"
cssGroup = [] if cssFile not in possibleList:
if not cdef[ "css" ] == "1": possibleList.append( cssFile )
cssGroup.append( cdef )
f = f.split( PY_SEP ) f = f.split( PY_SEP )
l = len( f ) l = len( f )
for i in range( 1, l ): for i in range( 1, l ):
key = PY_SEP.join( x for x in f[:-i] ) + PY_SEP + "_this.js" cssFile = PY_SEP.join( x for x in f[:-i] ) + PY_SEP + "@_this.css"
_def = self.resv.locate( key ) if cssFile not in possibleList:
possibleList.append( cssFile )
if _def and not _def[ "css" ] == "1": possibleList.sort()
cssGroup.append( _def )
for f in possibleList:
f = f.replace( "@_this.css", "_this.css" )
if os.path.exists( os.path.join( self.R, f ) ):
cssList.append( f )
cssGroup.sort( key = lambda x : x[ "src" ] )
cssList.extend( cssGroup )
def getCache( self, fileList, cName, mode ): def getCache( self, fileList, cName, mode ):
if self.CR == None: if self.CR == None:
return None return None
md5 = hashlib.md5( bytearray( "|".join( x[mode] for x in fileList ), "utf-8" ) ).hexdigest() md5 = hashlib.md5( bytearray( "".join( fileList ), "utf-8" ) ).hexdigest()
cName[0] = oFHash = md5 + "." + mode cName[0] = oFHash = md5 + "." + mode
cFHash = md5 + ".c." + mode cFHash = md5 + ".c." + mode
@ -204,14 +186,19 @@ class BotanClassResolver:
# Compressed file # Compressed file
cFile = os.path.join( self.CR, cFHash ) cFile = os.path.join( self.CR, cFHash )
cCached = self.useCache( cFile ) dates = list(
os.path.getmtime( os.path.join( self.R, x ) )
if os.path.exists( os.path.join( self.R, x ) ) else -1
for x in fileList
)
if self.flagCompress and cCached: # Root file date
return self.BotanCache( cFile, cFHash, self.returnDynamic ) dates.append( os.path.getmtime( os.path.join( self.R, "_this.js" ) ) );
if self.useCache( oFile ): if self.flagCompress and self.useCache( cFile, dates ):
return cFHash if self.returnHash else self.BotanCache( cFile )
if not cCached: elif self.useCache( oFile, dates ):
self.JWork.saveCache( self.JWork.saveCache(
oFile oFile
# Content is None to initiate a compression # Content is None to initiate a compression
@ -220,12 +207,19 @@ class BotanClassResolver:
, os.path.join( self.R, "externs" ) , os.path.join( self.R, "externs" )
) )
return self.BotanCache( oFile, oFHash, False ) return oFHash if self.returnHash else self.BotanCache( oFile )
return None def useCache( self, f, dList ):
if not os.path.exists( f ):
return False
def useCache( self, f ): t = os.path.getmtime( f )
return os.path.exists( f )
for i in dList:
if t < i:
return False
return True
def compileJs( self, cList, xList ): def compileJs( self, cList, xList ):
md5 = [ None ] md5 = [ None ]
@ -235,14 +229,14 @@ class BotanClassResolver:
cacheFile = self.getCache( cList, md5, "js" ) cacheFile = self.getCache( cList, md5, "js" )
if cacheFile is not None: if cacheFile != None:
return cacheFile; return cacheFile;
# The root file # The root file
outputJs = self.BotanFile( "_this.js" ) outputJs = self.BotanFile( "_this.js" )
for f in cList: for f in cList:
f = f[ "src" ]
path = ( path = (
os.path.splitext( f )[0] os.path.splitext( f )[0]
.replace( PY_SEP, "." ) .replace( PY_SEP, "." )
@ -254,7 +248,7 @@ class BotanClassResolver:
outputJs = wrapScope( outputJs ) outputJs = wrapScope( outputJs )
self.JWork.saveCache( [ self.JWork.saveCache if self.returnHash else self.JWork.saveCache ][0] (
os.path.join( self.CR, md5[0] ) os.path.join( self.CR, md5[0] )
, outputJs , outputJs
, "js" , "js"
@ -281,16 +275,17 @@ class BotanClassResolver:
md5 = [ None ] md5 = [ None ]
cacheFile = self.getCache( cList, md5, "css" ) cacheFile = self.getCache( cList, md5, "css" )
if cacheFile is not None: if cacheFile != None:
return cacheFile; return cacheFile;
struct = "/* @ */" outputCss = ""
outputCss = struct + self.BotanFile( "_this.css" )
for f in self.cleanList( cList ): for f in self.cleanList( cList ):
outputCss += self.BotanFile( f["src"][:-2] + "css" ) outputCss += self.BotanFile( f )
self.JWork.saveCache( os.path.join( self.CR, md5[0] ), outputCss, "css" ) [ self.JWork.saveCache if self.returnHash else self.JWork.saveCache ][0] (
os.path.join( self.CR, md5[0] ), outputCss, "css"
)
if self.returnHash: if self.returnHash:
return md5[0] return md5[0]
@ -304,26 +299,13 @@ class BotanClassResolver:
flag = mode[0] flag = mode[0]
requestAPIs = code requestAPIs = code
# Return compressed contents if possible
# otherwise return raw contents
if flag == "o": if flag == "o":
mode = mode[1:] mode = mode[1:]
# Return raw contents only
elif flag == "r": elif flag == "r":
mode = mode[1:] mode = mode[1:]
self.flagCompress = False self.flagCompress = False
# Return hashed filenames only
elif flag == "h":
mode = mode[1:]
self.returnHash = True
# Return hashed filenames if content is larger than self.oModeIfSizelt bytes
# otherwise act as "o" mode
else: else:
self.returnHash = True self.returnHash = True
self.returnDynamic = True
try: try:
requestAPIs = ( requestAPIs = (
@ -347,8 +329,7 @@ class BotanClassResolver:
for apis in requestAPIs: for apis in requestAPIs:
if not apis: if apis == None: continue
continue
classList = [] classList = []
lookupList = imports lookupList = imports

View File

@ -1,12 +1,10 @@
#!/usr/bin/env python3 #!/usr/bin/env python3
import os import os
from botanjs.compressor.closure import Wrapper as ClosureWrapper
from botanjs.compressor.yui import Wrapper as YUIWrapper
from botanjs.classmap import ClassMap from botanjs.classmap import ClassMap
if os.getenv( "UNIT_TEST" ) == "1": CeleryExists = True
CeleryExists = False
else:
CeleryExists = True
try: try:
from celery import Celery from celery import Celery
except ImportError: except ImportError:
@ -19,7 +17,7 @@ if CeleryExists:
if os.path.exists( "settings.ini" ): if os.path.exists( "settings.ini" ):
from botanjs.config import Config from botanjs.config import Config
app.conf.update( broker_url = Config["BotanJS"]["CeleryBroker"] ) app.conf.update( BROKER_URL = Config["BotanJS"]["CeleryBroker"] )
else: else:
from botanjs.dummy import app from botanjs.dummy import app
@ -36,11 +34,10 @@ class JWork:
if mode == "js": if mode == "js":
JWork.compressJs.delay( location, externs ) JWork.compressJs.delay( location, externs )
elif mode == "css": elif mode == "css":
JWork.compressCss( location ) JWork.compressCss.delay( location )
@app.task() @app.task()
def compressJs( md5, externs ): def compressJs( md5, externs ):
from botanjs.compressor.closure import Wrapper as ClosureWrapper
log.info( "Compress js: " + md5 ) log.info( "Compress js: " + md5 )
w = ClosureWrapper() w = ClosureWrapper()
w.scanExterns( externs ) w.scanExterns( externs )
@ -48,7 +45,6 @@ class JWork:
@app.task() @app.task()
def compressCss( md5 ): def compressCss( md5 ):
from botanjs.compressor.yui import Wrapper as YUIWrapper
log.info( "Compress css: " + md5 ) log.info( "Compress css: " + md5 )
w = YUIWrapper() w = YUIWrapper()
w.compress( md5 ) w.compress( md5 )
@ -58,6 +54,5 @@ class JWork:
log.info( "Building Class Map" ) log.info( "Building Class Map" )
c = ClassMap( src ) c = ClassMap( src )
os.makedirs( os.path.dirname( location ), exist_ok = True )
with open( location, "w" ) as f: with open( location, "w" ) as f:
f.write( c.build() ) f.write( c.build() )

20
botanjs/service/webapi.py Normal file → Executable file
View File

@ -1,10 +1,11 @@
#!/usr/bin/env python3
from flask import Flask from flask import Flask
from flask import Response from flask import Response
from flask import render_template from flask import render_template
from flask import request from flask import request
from botanjs.service.jclassresv import BotanClassResolver as JCResv from botanjs.service.jclassresv import BotanClassResolver as JCResv
from botanjs.service.jwork import app as CeleryApp, JWork from botanjs.service.jwork import app as CeleryApp, JWork
from botanjs.config import Config from botanjs.config import Config, DEBUG
import os import os
@ -23,28 +24,25 @@ class WebAPI:
self.BMap = os.path.join( self.BCache, "bmap.xml" ) self.BMap = os.path.join( self.BCache, "bmap.xml" )
if brokerURL != None: if brokerURL != None:
CeleryApp.conf.update( broker_url = brokerURL ) CeleryApp.conf.update( BROKER_URL = brokerURL )
self.app = Flask( __name__, static_url_path = "/cache/botanjs", static_folder = self.BCache ) self.app = Flask( __name__, static_url_path = self.BCache, static_folder = self.BCache )
self.app.jinja_env.add_extension( "compressinja.html.HtmlCompressor" ) self.app.jinja_env.add_extension( "compressinja.html.HtmlCompressor" )
self.app.add_url_rule( "/" , view_func = self.index ) self.app.add_url_rule( "/" , view_func = self.index )
self.app.add_url_rule( "/<mode>/" , view_func = lambda mode: self.api_request( mode, "zpayload" ) ) self.app.add_url_rule( "/<mode>/" , view_func = lambda mode: self.api_request( mode, "zpayload" ) )
self.app.add_url_rule( "/<mode>/<path:code>" , view_func = self.api_request ) self.app.add_url_rule( "/<mode>/<path:code>" , view_func = self.api_request )
def run( self, *args, **kwargs ): self.app.run(
JWork.buildClassMap( self.BRoot, self.BMap ) host = Config[ "Service" ][ "BindAddress" ]
return self.app.run( *args, **kwargs ) , port = int( Config[ "Service" ][ "Port" ] )
, debug = DEBUG )
def index( self ): def index( self ):
return "Hello, this is the BotanJS Service API.", 200 return "Hello, this is the BotanJS Service API.", 200
def api_request( self, mode, code ): def api_request( self, mode, code ):
if mode == "rebuild":
JWork.buildClassMap.delay( self.BRoot, self.BMap )
return "OK", 200
if code == "zpayload": if code == "zpayload":
code = request.args.get( "p" ) code = request.args.get( "p" )
@ -58,8 +56,6 @@ class WebAPI:
srvHandler = JCResv( JWork, self.BRoot, self.BMap, self.BCache ) srvHandler = JCResv( JWork, self.BRoot, self.BMap, self.BCache )
return Response( srvHandler.getAPI( code, mode = mode ), mimetype = t ) return Response( srvHandler.getAPI( code, mode = mode ), mimetype = t )
except Exception as e: except Exception as e:
if self.app.config[ "DEBUG" ]:
raise
return str(e), 404 return str(e), 404

View File

@ -1,554 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.AstroEdit" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {System.utils} */
var utils = __import( "System.utils" );
/** @type {System.utils.EventKey} */
var EventKey = __import( "System.utils.EventKey" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMObject} */
var IDOMObject = __import( "Dandelion.IDOMObject" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
/** @type {Astro.Blog.Components.Bubble} */
var Bubble = __import( "Astro.Blog.Components.Bubble" );
var opostData = __import( "System.Net.postData" );
var prettyDate = __import( "Astro.utils.Date.pretty" );
var Visualizer = ns[ NS_INVOKE ]( "Visualizer" );
var Flag = ns[ NS_INVOKE ]( "Flag" );
// Editor Override
var postData = function( processor, data, success, failed )
{
data[ "editor" ] = 1;
opostData( processor, data, success, failed );
};
// Wrappers for every plugins
var PluginBundles = function( article, plugins )
{
this.plugins = plugins;
for( var i in this.plugins )
{
/* @type {Astro.Blog.AstroEdit.IPlugins} */
var g = this.plugins[i];
g.bindArticle = article;
}
};
PluginBundles.prototype.setForView = function( pluginId, data )
{
for( var i in this.plugins )
{
var p = this.plugins[i];
if( p.id == pluginId )
{
p.setForView( data );
}
}
};
PluginBundles.prototype.getData = function( pluginId, data )
{
for( var i in this.plugins )
{
var p = this.plugins[i];
if( p.id == pluginId )
{
return p.getData( data );
}
}
};
var Article = function( processorSet, plugins )
{
var pBubble = new Bubble();
var Draft = ns[ NS_INVOKE ]( "Draft" );
var _title = "";
var _content = "";
//// Classes & obj
var _visualizer = null;
var timestamp = new Date();
/** @type {_AstJson_.AJaxGetArticle.entry} */
var ArticleModel = {
title: ""
, slug: ""
, content: ""
, date_modified: timestamp
, date_published: timestamp
, date_created: timestamp
, archived: false
, tags: null
, section: null
, draft: true
, article_id: false
};
var ae_content = Dand.id( "ae_content" );
var ae_title = Dand.id( "ae_title" );
// Article info
var ae_cdate = Dand.id( "ae_cdate" );
var ae_mdate = Dand.id( "ae_mdate" );
var ae_pdate = Dand.id( "ae_pdate" );
var ae_status = Dand.id( "ae_status" );
var ae_backup = Dand.id( "ae_backup_btn" );
var ae_publish = Dand.id( "ae_publish_btn" );
var ae_preview = Dand.id( "ae_preview" );
/** @type {_AstConf_.AstroEdit} */
var a_conf = Config.get( "AstroEdit" );
var base_path = utils.siteProto( Config.get( "BasePath" ) );
/*{{{ preview fields */
var ae_p_fields = {
mtime: set_field_name( Dand.wrap( "input" ), "date_modified" )
, ptime: set_field_name( Dand.wrap( "input" ), "date_published" )
, title: set_field_name( Dand.wrap( "input" ), "title" )
, content: set_field_name( Dand.wrap( "input" ), "content" )
, tags: set_field_name( Dand.wrap( "input" ), "tags" )
, section: set_field_name( Dand.wrap( "input" ), "section" )
};
// Initialize id
var __article_id = false;
var canSave = false;
var temp;
for ( var i in ae_p_fields ) ae_preview.appendChild( ae_p_fields[i] );
/* End preview fields }}}*/
/*{{{ Button sections */
var ae_stitles = Dand.glass( "ae_stitle", true );
var ae_panel_section = Dand.glass( "ae_panel_section", true );
var l = ae_stitles.length;
for( var i = 0; i < l; i ++ )
{
var t = ae_stitles[i];
var p = ae_panel_section[i];
// If they are snippets or sections
if( i == 2 || i == 3 )
{
p.style.height = "auto";
continue;
}
t.addEventListener( "Click", function( e )
{
var p = this.p;
if( this.t.expanded = !this.t.expanded )
{
p.style.height = "auto";
Cycle.next(
function(){
p.style.height = this.h + "px";
}.bind({ h: p.element.clientHeight })
);
p.style.height = 0;
}
else
{
p.style.height = 0;
}
}.bind({ t: t, p: p }) );
}
ae_stitles[0].element.click();
/* End Button sections }}}*/
// Install plugins
plugins = new PluginBundles( this, plugins );
var enableSaveFunction = function ()
{
ae_backup.className = "ae_iValue ae_dodgerblue flsf";
canSave = true;
}
, disableSaveFunction = function ()
{
ae_backup.className = "ae_iValue ae_disabled flsf";
canSave = false;
}
, contentUpdate = function ()
{
if( !canSave ) enableSaveFunction();
// (_visualizer.saveRaw() != _content) ? enableSaveFunction() : disableSaveFunction();
}
//// private methods
////// Handlers ///////
, saveSuccess = function ( obj )
{
disableSaveFunction();
ae_mdate.innerHTML = prettyDate( new Date( obj.date_modified ) );
// Replace state of the content and title
ArticleModel.title = _title;
ArticleModel.content = _content;
ArticleModel.date_modified = obj.date_modified;
// If this is a published article
// we need to set the ref_id for ArticleModel
// then set current id to draft's id
if( ArticleModel.article_id != obj.article_id )
{
ArticleModel.draft = true;
ArticleModel.ref_id = __article_id;
ArticleModel.article_id = obj.article_id;
}
// Set article id if this is a new document
if ( obj.article_id )
ArticleModel.article_id = __article_id = obj.article_id;
window.history.replaceState( ArticleModel, "", base_path + "astroedit/" + __article_id + "/" );
}
, publishSuccess = function ( obj )
{
saveSuccess( obj );
ae_publish.innerHTML = "Done edit";
ae_backup.innerHTML = "Backup(Ctrl + s)";
ArticleModel.date_published = obj.date_published;
ae_pdate.innerHTML = prettyDate( new Date( obj.date_published ) );
this.contentUpdate && saveSuccess( obj );
new MessageBox(
"AstroEdit"
, "You have successfully published your article!"
, "Stay here", "Exit and goto article"
, publishAction
).show();
}
, publishAction = function ( stay )
{
if ( !stay )
{
var op = window.open( base_path + "article/id-view/" + ArticleModel.article_id + "/" );
Cycle.next( function() {
if( op ) window.close();
});
}
}
, restoreArticle = function( obj )
{
debug.Info("[Document] Looking for stored data");
if ( obj )
{
debug.Info("[Document] .. data found");
// Set stored article id
__article_id = obj.article_id;
setArticle( obj );
}
else
{
if (!( ArticleModel && 0 < ArticleModel.article_id ))
{
debug.Info("[Document] .. data not found");
// This is a state of new article
var d = Math.floor(new Date().getTime()/1000);
__article_id = false;
setArticle({
title:""
, content:""
, date_modified: d
, date_published: 0
, date_created: d
, archived: false
, tags: null
, draft: true
, article_id: false
});
window.history.replaceState( ArticleModel, "", base_path + "astroedit/new/" );
}
}
}
/** @param {_AstJson_.AJaxGetArticle} */
, showArticle = function( obj )
{
if ( obj && obj.entry )
{
debug.Info( "[Document] Article Loaded" );
if ( obj.entry.ref_id )
{
// This is a backup item
__article_id = obj.article_id;
pBubble.setColor( "royalblue" );
pBubble.pop( "Using backup entry" );
Cycle.delay( function () { pBubble.blurp() }, 3000 );
}
setArticle( obj.entry );
__statePusher( obj.entry, __article_id );
}
else
{
debug.Info( "[Document] Article: " + String( __article_id ) + " not found on server." );
__article_id = false;
}
}
, setArticle = function ( entry )
{
ArticleModel = entry;
ae_title.value = _title = ArticleModel.title;
_visualizer.visualizeData( _content = ArticleModel.content );
ae_mdate.innerHTML = prettyDate( new Date( ArticleModel.date_modified ) );
ae_cdate.innerHTML = prettyDate( new Date( ArticleModel.date_created ) );
ae_pdate.innerHTML = ArticleModel.date_published
? prettyDate( new Date( ArticleModel.date_published ) )
: "Not published."
;
ae_status.innerHTML =
( ArticleModel.archived ? "Archived. " : "" )
+ ( ArticleModel.draft ? "In draft" : "Published" )
;
ae_publish.innerHTML = ArticleModel.draft ? "Publish" : "Done edit";
ae_backup.innerHTML = ( ArticleModel.draft ? "Save" : "Backup" ) + "(Ctrl + s)";
plugins.setForView( "tags", ArticleModel.tags );
plugins.setForView( "section", ArticleModel.section );
}
, deleteDraft = function ( confirmed )
{
if ( confirmed )
{
var _data = {
"draft": ArticleModel.draft ? 1 : 0
, "article_id": __article_id
, "del": 1
};
postData( processorSet, _data, deleteSuccess, serverFailed );
}
}
, deleteSuccess = function ( obj )
{
var loc = window.location;
loc.replace(
loc.href.replace(
"/" + ArticleModel.article_id
, ArticleModel.ref_id ? ( "/" + ArticleModel.ref_id ) : ""
)
);
}
, serverFailed = function ( obj )
{
pBubble.setColor( "red" );
pBubble.pop( obj ? obj["mesg"] : "Server Error" );
Cycle.delay( function () { pBubble.blurp() }, 3000 );
}
, contentEmpty = function ()
{
return !Boolean( ae_content.hasChildNodes() );
}
;
// Bind properties
this.saveOrBackup = function ()
{
if ( canSave )
{
// Store current content and title
_title = ae_title.value.trim();
_content = _visualizer.saveRaw();
/** @type {_AstJson_.AJaxGetArticle.entry} */
var _data =
{
article_id: __article_id ? __article_id : ""
, title: _title
, content: _content
, draft: 1
, tags: plugins.getData( "tags" )
, section: plugins.getData( "section" )
};
postData( processorSet, _data, saveSuccess, serverFailed );
}
};
this.load = function ( aid, statePusher )
{
if( aid && __article_id != aid )
{
debug.Info( "[Document] Loading article: " + aid );
__statePusher = statePusher;
postData(
a_conf.paths.get_article
, { article_id: __article_id = aid }
, showArticle
, serverFailed
);
}
};
this.getArticleId = function () { return __article_id; }
this.preview = function ()
{
ae_p_fields.title.value = ae_title.value;
ae_p_fields.content.value = _visualizer.saveRaw();
ae_p_fields.mtime.value = ArticleModel.date_modified;
ae_p_fields.ptime.value = Number( ArticleModel.date_published )
? ArticleModel.date_published
: Math.floor( 0.001*( new Date().getTime() ) )
;
ae_p_fields.tags.value = plugins.getData( "tags" );
ae_p_fields.section.value = plugins.getData( "section" );
ae_preview.submit();
};
this.invoke = function (_class)
{
if ( _class instanceof Draft ) _ae_draft = _class;
if ( _class instanceof Visualizer )
{
_visualizer = _class;
_visualizer.setContentDiv( ae_content );
}
};
this.saveAndPublish = function ()
{
if ( contentEmpty() ) return;
/** @type {_AstJson_.AJaxGetArticle.entry} */
var _data = {
article_id: __article_id ? __article_id : ""
, draft: 0
};
if ( !ArticleModel.draft )
{
// This is a published article
canSave = true;
}
if ( canSave )
{
// Store current content and title
_title = ae_title.value.trim();
_content = _visualizer.saveRaw();
_data.title = _title;
_data.content = _content;
_data.tags = plugins.getData( "tags" );
_data.section = plugins.getData( "section" );
postData( processorSet, _data, publishSuccess.bind({ contentUpdate: true }), serverFailed );
}
else
{
// Do not submit uneccessary data!
postData( processorSet, _data, publishSuccess, serverFailed );
}
};
this.drop = function ()
{
if( ArticleModel.draft )
{
new MessageBox(
"Delete draft"
, "Are you sure you want to delete this draft? (Published article will only remove backup draft.)"
, "Delete", "No"
, deleteDraft
).show();
}
else
{
new MessageBox(
"Delete Draft"
, "There is no draft to delete"
).show();
}
};
this.updateContent = contentUpdate;
// Setting Ctrl+s functions
new IDOMObject(document).addEventListener(
new EventKey("KeyDown", function(e)
{
// key Ctrl(17)
if(e.ctrlKey == true && e.which == 83)
{
// key s (83)
this.saveOrBackup();
e.preventDefault();
}
}.bind(this))
);
IDOMElement( ae_backup ).addEventListener( "Click", this.saveOrBackup );
window.addEventListener(
"popstate"
, function( event )
{
debug.Info( "[Document] Pop State fired" );
restoreArticle( event.state );
}
);
ae_title.oninput = function ()
{
( ae_title.value != _title ) ? enableSaveFunction() : disableSaveFunction();
}
temp = IDOMElement(ae_content);
temp.addEventListener( "Input", function() { enableSaveFunction(); } );
document.body.appendChild( pBubble.init() );
return this;
};
var set_field_name = function ( elem, value )
{
elem.name = value;
elem.type = "hidden";
return elem;
};
ns[ NS_EXPORT ]( EX_CLASS, "Article", Article );
})();

View File

@ -1,158 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.AstroEdit" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
var postData = __import( "System.Net.postData" );
/** @param {Astro.Blog.AstroEdit.Article} article */
var Draft = function ( article, draftsUri )
{
/** @type {Astro.Blog.AstroEdit.Article} */
var Article = ns[ NS_INVOKE ]( "Article" );
if ( !( article instanceof Article ) ) return;
// Drafts Container
var ae_expand = Dand.id("ae_expand")
, ae_drafts = Dand.id("ae_user_drafts")
, ae_drafts_h = null
////// Draft Section
, showDrafts = function ()
{
showDrafts = function() { };
// One-time trigger only.
getDraftList({offset: 0});
}
, getDraftList = function ( p )
{
postData( draftsUri, p, listDraft.bind(p), draftFailed );
}
/** @param {_AstJson_.AJaxGetDrafts} obj */
, listDraft = function ( obj )
{
var entries = obj.entries, entry;
for ( var i in entries )
{
/** @param {_AstJson_.AJaxGetDrafts.entry} */
entry = entries[i];
// Insert entries
ae_drafts.appendChild(
entry = Dand.wrapc(
"ae_dEntry"
, [
Dand.wrapc(
"ae_dEntry_title fls"
, entry.active
?
[
Dand.textNode( entry.title )
, Dand.wrap( "span", null, "ae_dActive_bubble", "\u25CF" )
]
: entry.title
)
, Dand.wrapc( "ae_dEntry_content flsf", entry.content )
, Dand.wrapc( "ae_dEntry_date fsf", entry.date )
]
, entry.active
? [ new IKey ( "value", entry._id ), new IKey( "active" ) ]
: new IKey( "value", entry._id ) )
);
// Register on click function
entry.addEventListener( "click", function() {
article.load( this.getAttribute( "value" ), __pushState );
}.bind( entry ) );
}
ae_drafts_h = ae_drafts.clientHeight;
ae_drafts.style.height = 0;
Cycle.next(function(){
// This doesn't make sense
// but we need to actually access the clientHeight
// to get the height animation working
ae_drafts.clientHeight;
ae_drafts.style.height = String( ae_drafts_h ) + "px";
});
}
, draftFailed = function (obj)
{
}
// Handlers
, setupExpand = function ()
{
ae_expand.className = "ae_expand_btn";
var panel = Dand.id("ae_minor_panel");
panel.onmouseover = function()
{
ae_expand.style.height = "20px";
}
panel.onmouseout = function()
{
ae_expand.style.height = "";
}
panel.onclick = function()
{
ae_expand.style.height = "";
ae_drafts.style.height = String(ae_drafts_h) + "px";
Cycle.delay(setupCollapse , 250);
// Disable mouse events
panel.onmouseover = panel.onmouseout = panel.onclick = null;
showDrafts();
}
}
, setupCollapse = function ()
{
ae_expand.className = "ae_callapse_btn";
Cycle.delay(function()
{
ae_expand.onclick = function()
{
ae_expand.style.backgroundColor = "";
ae_drafts.style.height = "0";
Cycle.delay(setupExpand, 250);
// Disable mouse events
ae_expand.onmouseover = ae_expand.onmouseout = ae_expand.onclick = null;
}
ae_expand.onmouseover = function()
{
ae_expand.style.backgroundColor = "rgba(255, 255, 255, 0.2)";
}
ae_expand.onmouseout = function()
{
ae_expand.style.backgroundColor = "";
}
}, 250);
}
// End Handlers
, __pushState = function ( obj, article_id )
{
window.history.pushState( obj, "", "/astroedit/" + article_id + "/" );
}
setupExpand();
article.invoke( this );
};
ns[ NS_EXPORT ]( EX_CLASS, "Draft", Draft );
})();

View File

@ -1,27 +0,0 @@
.flag_active {
color: white;
opacity: 1 !important;
}
.ae_flag_delete {
color: white;
padding: 0 0.5em 0 0;
}
.ae_flag_delete:hover {
color: red;
}
.ae_flag_add {
color: white;
cursor: default;
font-weight: 200;
}
.ae_flag_add:hover {
color: dodgerblue;
}
.ae_flags > span {
float: left;
}

View File

@ -1,190 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.AstroEdit" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
var postData = __import( "System.Net.postData" );
/* @type {AstroEdit.IPlugins} */
var Flag = function ( id, target, flagConf )
{
this.id = id;
var stage = Dand.id( target );
var ae_addFlag = Dand.glass( "ae_flag_add" , true, stage )[0];
var ae_flags = Dand.glass( "ae_flags" , false, stage )[0];
// Store flags for future use
var flags = {};
////// Handlers
ae_addFlag.addEventListener(
"Click", function ( e )
{
e.stopPropagation();
// Input fields
var ae_flagInput;
// Popup MessageBox
new MessageBox(
"Add new flag(s)"
, Dand.wrape([
Dand.wrapc(
"v_instruction flsf"
, "Flags are separated by \\n. (existing flags will be ignored.)"
)
, ae_flagInput = Dand.wrap( "textarea", null, "v_snippet_input" )
])
, "OK", "Cancel"
, parseFlags.bind( ae_flagInput )
).show();
}
);
var deleteFlag = function (e)
{
e.stopPropagation();
var p = { stage: this.parentNode };
p[ id ] = this.nodeValue;
p[ "id" ] = id;
postData( flagConf.URICount, p, confirmDelete.bind( p ), serverFailed );
};
var confirmDelete = function (obj)
{
new MessageBox(
"Delete Flag"
, [
Dand.wrapc("ae_blockswitch",
[
Dand.textNode( "Are you sure you want to delete " )
, Dand.wrap( "span", null, "flag_active", Dand.textNode( this[ id ] ) )
, Dand.textNode( " ?." )
]
)
, obj.count > 0
? Dand.wrape([
Dand.textNode( "This will affect " )
, Dand.wrap(
"span", null, "ae_affected_count", Dand.textNode( obj.count )
)
, Dand.textNode(" article(s).")
])
: null
]
, "Delete", "No"
, doDelete.bind( this )
).show();
};
var doDelete = function( confirmed )
{
if ( confirmed )
{
this[ "del" ] = 1;
postData(
flagConf.URISet
, this
, deleteSuccess.bind( this )
, serverFailed
);
}
};
var deleteSuccess = function(obj)
{
// Remove element
this.stage.parentNode.removeChild( this.stage );
// Delete reference
delete flags[ this[ id ] ];
};
var parseFlags = function ()
{
// Filter invalid flags
var nflags = this.value.trim().match(/[^\n]+/g), d, e;
for (var i in nflags)
{
if(!flags[(i = nflags[i]).toLowerCase()])
{
flags[i] = Dand.wrap("span", null, "flag_active",
[d = Dand.wrap("span", null, "ae_flag_delete", "\u00D7"), e = Dand.textNode(i)]
);
// Seperator
ae_flags.appendChild(Dand.textNode(" "));
ae_flags.appendChild(flags[i]);
flags[i].onclick = function() { toggleFlag(this) }.bind(flags[i]);
d.onclick = deleteFlag.bind(e);
}
else
{
debug.Info("Flag exist: " + i);
// Hightlight these flags
flags[i.toLowerCase()].className = "flag_active";
}
}
};
var toggleFlag = function (flag)
{
var isEnabled = flag.className == "flag_active" ? true : false;
flag.className = isEnabled ? "ae_disabled" : "flag_active";
};
var serverFailed = function (obj) { };
var cflag, ae_children = ae_flags.childNodes;
for (var i in ae_children)
{
if((cflag = ae_children[i]).nodeType == 1)
{
flags[cflag.lastChild.nodeValue.toLowerCase()] = cflag;
IDOMElement( cflag ).addEventListener( "Click", function() { toggleFlag( this ); }.bind( cflag ) );
// Bind the last child (x button) to firstChild (textNode: flagname)
IDOMElement( cflag.firstChild ).addEventListener( "Click", deleteFlag.bind( cflag.lastChild ) );
}
}
this.getData = function ()
{
// Compile flag list
var tlist = [];
// Return names
for (var i in flags)
{
if(flags[i].className == "flag_active")
tlist[tlist.length] = flags[i].lastChild.nodeValue;
}
return tlist.join("\n");
}
this.setForView = function ( flagList )
{
// Disable all flags first
for ( var i in flags ) flags[i].className = "ae_disabled";
// Set flags from flagList
for ( i in flagList )
if ( flagList[i] ) flags[flagList[i].toLowerCase()].className = "flag_active";
}
}
Flag.prototype.getSetData = function () { };
Flag.prototype.setForView = function ( flagList ) { };
ns[ NS_EXPORT ]( EX_CLASS, "Flag", Flag );
})();

View File

@ -1,415 +0,0 @@
#siteLibrary {
position: fixed;
width: 100%;
height: 100%;
top: calc(-100% - 5px);
}
#siteLibrary:hover {
top: calc(-100% + 1.5em);
}
#asl_viewer {
width: calc(100% - 300px);
height: 100%;
overflow-x: hidden;
overflow-y: scroll;
float: left;
position: relative;
}
.asl_colls.canvasGeneral {
color: #BBB;
}
.canvasGeneral.asl_colls > div > span.c75 { width: 75%; }
.canvasGeneral.asl_colls > div > span.c25 { width: 25%; }
.asl_header {
width: 100%;
height: 20px;
top: 100%;
margin-top: -20px;
position: absolute;
z-index: 1;
}
#asl_viewer > #canvasView {
position: absolute;
min-height: 100%;
width: 100%;
}
.asl_viewer {
width: 100%;
height: 100%;
background: #EEE;
-moz-box-shadow: 0 7px 5px black;
-webkit-box-shadow: 0 7px 5px black;
box-shadow: 0 7px 5px black;
}
.asl_contentMenu {
bottom: 0;
position: absolute;
padding: 1em;
}
.asl_contentMenu > span {
margin: 0 0.2em;
padding: 0.5em 0.5em;
cursor: default;
color: white;
background-color: rgba(0, 0, 0, 0.6);
font-family: custom-serif;
}
.asl_contentMenu > span:hover {
background-color: rgba(0, 0, 0, 0.8);
}
.asl_contentMenu > span[current] {
background-color: rgba(0, 0, 0, 0.8);
}
.asl_smask {
height: 10px;
background-color: royalblue;
position: absolute;
bottom: -5px;
width: 100%;
}
.asl_smask:before {content: '';
width: 100%;
height: 20px;
top: -10px;
position: absolute;
z-index: -1;
background-color: transparent;
}
.asl_smask[expand] {
background-image: url(/assets/blog/layout-images/collapse.png);
background-position: center 2.5px;
background-repeat: no-repeat;
}
.asl_smask[expand]:hover {
height: 20px;
}
#siteLibrary .asl_title, .asl_intitle {
font-size: 1.5em;
font-family: custom-sans;
overflow: hidden;
background-color: royalblue;
color: white;
}
#siteLibrary .asl_title {
padding: 0.3em 0.5em;
}
.asl_contentPanel {
overflow: hidden;
position: absolute;
height: calc(100% - 2.5em);
width: 100%;
}
#siteLibrary .asl_title {
cursor: default;
display: inline-block;
position: absolute;;
right: 350px;
bottom: -1.7em;
-moz-box-shadow: 2px 2px 5px black;
-webkit-box-shadow: 2px 2px 5px black;
box-shadow: 2px 2px 5px black;
}
/*** ASL Canvases ***/
.canvasImage > span {
width: 100px;
height: 100px;
margin: 0.2em;
background-repeat: no-repeat;
background-position: center;
border: 1px solid transparent;
display: inline-block;
vertical-align: middle;
position: relative;
overflow: hidden;
}
.canvasImage > span:before {
content: '';
display: inline-block;
height: 100%;
vertical-align: middle;
}
.canvasImage > span img {
vertical-align: middle;
display: inline-block;
}
.canvasImage > span:after {
content: attr(data-title);
background-color: rgba(0,0,0,0.6);
color: white;
position: absolute;
left: 0;
bottom: -2em;
font-size: 0.8em;
width: 100%;
padding-left: 0.5em;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
-webkit-transition: all .25s ease-out;
-moz-transition: all .25s ease-out;
-o-transition: all .25s ease-out;
transition: all .25s ease-out;
}
.canvasImage > span:hover:after {
bottom: 0%;
}
.canvasImage > span[selected] {
background-color: lightblue;
border-color: royalblue;
}
.canvasImage > span > span {
width: 100%;
height: 100%;
display: block;
}
.canvasImage > span > span:hover {
background-color: rgba(0, 0, 0, 0.2) !important;
border-color: #444 !important;
}
.ci_album {
-moz-box-shadow: 2px 3px 0 0 black;
-webkit-box-shadow: 2px 3px 0 0 black;
box-shadow: 2px 3px 0 0 #666;
border: 1px solid #666 !important;
}
.canvasGeneral {
padding: 0.2em;
cursor: default;
color: #444;
}
.canvasGeneral > div {
padding: 0.2em;
}
.canvasGeneral > div:hover {
background-color: rgba(0, 0 ,0, 0.2);
}
.canvasGeneral > div > span {
display: inline-block;
width: 30%;
padding: 0.2em 0;
overflow: hidden;
text-overflow: ellipsis;
}
.canvasGeneral > div > span:last-child {
width: 10%;
}
.canvasGeneral > div[selected] {
background-color: orangered;
color: white;
}
/*** End ASL Canvases ***/
/*** Uploader ***/
#asl_uploader {
width: 300px;
height: 100%;
float: right;
font-family: custom-sans;
}
#asl_u_head {
position: absolute;
background: #EEE;
z-index: 1;
}
.upldr_title {
font-size: 1.5em;
}
.asl_fwrapper {
overflow-y: scroll;
position: absolute;
top: 0;
width: 100%;
height: 100%;
/*
-moz-box-shadow: inset 0 0 20px black;
-webkit-box-shadow: inset 0 0 20px black;
box-shadow: inset 0 0 20px black;
*/
}
.asl_fileList {
font-family: sans-serif;
color: #444;;
cursor: default;
}
.asl_fileList > div {
/* 0.5em for fwrapper padding */
margin-right: 50%;
padding: 0.5em;
overflow: hidden;
text-overflow: ellipsis;
}
.asl_uItem:hover {
background-color: rgba(0, 0, 0, 0.2);
}
.asl_uItemStat {
padding: 0 0.5em 0 0;
color: orange;
}
.asl_split {
position: relative;
height: 80px;
overflow: hidden;
}
.asl_split > div {
height: 100%;
padding: 0.5em;
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
}
.asl_left {
float: left;
width: 135px;
}
.asl_right {
float: right;
width: calc(100% - 135px);
}
.asl_fileName {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.asl_preview {
padding: 0.2em;
background-color: white;
height: 100%;
}
/* Progress indicator */
.asl_progress {
padding: 0.5em 0;
}
.asl_ptext {
font-size: 0.8em;
}
.asl_pbar {
background-color: white;
position: relative;
height: 1em;
margin-top: 0.2em;
}
.asl_pbar_fill {
background: greenyellow;
position: absolute;
width: 0%;
height: 100%;
}
.asl_go_up {
width: 0;
height: 0;
border-top: 0 solid transparent;
border-bottom: 0.5em solid transparent;
border-left: 0.5em solid #FFF;
position: absolute;
left: 0;
}
.asl_btn {
padding: 0.3em;
text-align: center;
cursor: default;
}
.asl_btn:hover {
background-color: rgba( 0, 0, 0, 0.2);
}
.asl_instruction {
width: 100%;
height: 100%;
font-size: 0.8em;
}

View File

@ -1,768 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.AstroEdit" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
/** @type {System.utils.Perf} */
var Perf = __import( "System.utils.Perf" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {System.utils.EventKey} */
var EventKey = __import( "System.utils.EventKey" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
/** @type {Components.Mouse.ContextMenu} */
var ContextMenu = __import( "Components.Mouse.ContextMenu" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMObject} */
var IDOMObject = __import( "Dandelion.IDOMObject" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Blog.Config} */
var Conf = __import( "Astro.Blog.Config" );
var postData = __import( "System.Net.postData" );
var prettyDate = __import( "Astro.utils.Date.pretty" );
var SiteLibrary = function ( basePath, processorGet, processorSet )
{
var view_index = []
, currentView
, inCollection = 0
, indexingItem
, itemSelected = false
, holdingCtrl = false
, holdingShift = false
/** @type {_AstConf_.SiteFile} */
, config = Conf.get( "SiteFile" )
, contentPanel = Dand.id("asl_viewer")
, canvasView
, contextMenu
, stage = Dand.id( "siteLibrary", true )
, asl_smask = Dand.id( "asl_smask", true )
, getItemKeys = function (data)
{
return [
new DataKey("id", data.id)
, new IKey("data-title", data.name)
, new IKey("data-author", data.author)
, new DataKey("hash", data.hash)
];
}
, bindData = function(target, source, data)
{
IDOMElement(source).addEventListener(new EventKey("MouseDown", function (e)
{
// pass neccessary informations for contextMenu to read
target.idata = this;
if(e.which == 1 || (e.which == 3 && !this.stage.hasAttribute("selected")))
{
// Mousedown event will bubble up to parent node, set itemselected to true
itemSelected = true;
if( !holdingCtrl ) deselectAllItem.bind( target )();
if(holdingShift) rangedSelect();
else indexingItem = this.stage;
selectItem.bind(target)();
}
}.bind(
{
stage: source
, id: data.id
, href: data.src_location
, hash: data.hash
, author: data.author
, name: data.name
, date: data.date_created
, isCollection: 0 < data.cCount
}
)));
}
////// Canvas builders
, resetCanvas = function (name)
{
if(canvasView)
{
contentPanel.removeChild(canvasView);
contentPanel.appendChild(canvasView = Dand.wrap(null, "canvasView", name || canvasView.getAttribute("class"), null, new DataKey("name", currentView)));
}
else
{
contentPanel.appendChild(canvasView = Dand.wrap(null, "canvasView", name, null, new DataKey("name", currentView)));
}
IDOMElement(canvasView).addEventListener(
new EventKey("Click", function (e)
{
if(e.which == 1)
{
if(!itemSelected)
{
deselectAllItem.bind(canvasView)();
canvasView.idata = null;
}
itemSelected = false;
}
}
)
);
}
, buildAudioCanvas = function (e)
{
// TODO
resetCanvas("canvasAudio");
}
/** @param {_AstJson_.AJaxGetFiles} */
, buildImageCanvas = function ( e )
{
var f = e.files;
resetCanvas( "canvasImage" );
for( var i in f )
{
/** @param {_AstJson_.AJaxGetFiles.file} */
var file = f[i];
// id: i, name: file.name, hash: file.hash, sorce: file.src_location, date: file.date_created
var img = Number( file.cCount )
////// Album item
? Dand.wrap(
"span", "img_" + Perf.uuid, "ci_album"
, Dand.wrapna( "img", new IKey( "src", basePath + "image/s100/" + file.hash + ".jpg" ) )
, [
new IKey("title"
, "Album: " + file.name
+ "\n" + file.cCount + " file(s)"
+ "\nDate: " + prettyDate( new Date( file.date_created ), true )
+ "\nCreated by: " + file.author
)
, new IKey("collection", 1)
].concat( getItemKeys( file ) )
)
//////// Normal filele
: Dand.wrap(
"span", "img_" + Perf.uuid, null
, Dand.wrapna( "img", new IKey( "src", basePath + "image/s100/" + file.hash + ".jpg" ) )
, [
new IKey("title"
, "File: " + file.name
+ "\nDate: " + prettyDate( new Date( file.date_created ), true )
+ "\nCreated by: " + file.author
)
].concat( getItemKeys( file ) )
);
canvasView.appendChild( img );
bindData( canvasView, img, file );
}
contextMenu = new ContextMenu(canvasView, [
new EventKey("Open", openAction)
, {
name: "Copy"
, items: [
new EventKey("Copy source link", copyItemLink)
, new EventKey("Copy hash", copyHash)
]
}
, {
name: "Selection"
, items: [
{
name: "Select"
, items: [
new EventKey("all", selectAllItem)
, new EventKey("none", deselectAllItem)
, new EventKey("Invert selection", reverseSelection)
]
}
,{
name: "By type"
, items:
[
new EventKey("Only albums", selectAllCollections)
, new EventKey("Only files", selectAllFiles)
]
}
]
}
, {
name: "Action"
, items: [
new EventKey("Group selected file(s)", setCollection)
, new EventKey("Add file(s) to collection", insertCollection)
// TODO: in-group file action changes
, new EventKey("Move file(s) to collection", function(){})
, new EventKey("Remove files(s) from collection", excludeCollection)
]
}
,new EventKey("Refresh", refreshCanvas)
, new EventKey("Rename", popupRename)
, new EventKey("Delete", confirmDelete)
], "RMB");
}
// General file, list view
/** @param {_AstJson_.AJaxGetFiles} */
, buildGeneralCanvas = function ( e )
{
if( !e ) return;
var f = e.files, dateStamp;
resetCanvas( "canvasGeneral" );
for(var i in f)
{
/** @param {_AstJson_.AJaxGetFiles.file} */
var file = f[i];
dateStamp = Dand.wrap( "span" );
dateStamp.innerHTML = prettyDate( new Date( file.date_created ) ) ;
var li = Dand.wrap(
null, "g_item" + Perf.uuid, null
, [
Dand.wrapne( "span", file.name )
, dateStamp
, Dand.wrapne( "span", file.author )
]
, getItemKeys( file )
);
canvasView.appendChild( li );
bindData( canvasView, li, file );
}
contextMenu = new ContextMenu(canvasView, [
{
name: "Copy"
, items: [
new EventKey("Copy source link", copyItemLink)
, new EventKey("Copy hash", copyHash)
]
}
, new EventKey("Delete file", confirmDelete)
], "RMB");
}
, selHasCollection = false
// Return the selected files
, selections = function(return_id) {
var s = [];
selHasCollection = false;
IDOMElement(canvasView).foreach(1, function(elem) {
// Save the hashes
if(elem.hasAttribute("selected"))
{
s[s.length] = return_id ? IDOMElement(elem).getDAttribute("id") : elem;
if(elem.hasAttribute("collection")) selHasCollection = true;
}
});
return s;
}
/// Menu item handlers
, confirmDelete = function ()
{
new MessageBox("Confirm delete"
, [
Dand.wrape("Are you sure you want to delete the selected item(s)?")
, Dand.wrape("Warning: This action cannot be undone! Make sure you have de-referenced them from your articles.", new IKey("style", "color: yellow;"))
]
, "Delete it", "No"
, requestDelete.bind({files: selections()})).show();
}
, popupRename = function ()
{
var name_field = Dand.wrap("input", null, "v_snippet_input_single", null, new IKey("type", "text"));
new MessageBox("Rename \"" + canvasView.idata.name + "\"", name_field, "OK", "Cancel", requestRename.bind(
{
name: name_field
, stage: canvasView.idata.stage
, isCollection: canvasView.idata.isCollection
}
)).show();
}
, copyItemLink = function () { return config.f_host + canvasView.idata.href; }
, copyHash = function ()
{
var data = canvasView.idata;
return data.isCollection ? data.id : data.hash;
}
, openAction = function ()
{
if(canvasView.idata.isCollection) openCollection(IDOMElement(canvasView.idata.stage).getDAttribute("id"));
else window.open( config.f_host + canvasView.idata.href);
}
//// ContextMenu Handlers: Selections
, selectItem = function()
{
canvasView.idata.stage.hasAttribute("selected") ? canvasView.idata.stage.removeAttribute("selected") : canvasView.idata.stage.setAttribute("selected", 1);
}
, selectAllItem = function ()
{
IDOMElement(canvasView).foreach(1, function(target)
{
target.setAttribute("selected", 1);
});
}
, selectAllCollections = function ()
{
IDOMElement(canvasView).foreach(1, function(target)
{
target.hasAttribute("collection") ? target.setAttribute("selected", 1) : target.removeAttribute("selected");
});
}
, selectAllFiles = function ()
{
IDOMElement(canvasView).foreach(1, function(target)
{
target.hasAttribute("collection") ? target.removeAttribute("selected") : target.setAttribute("selected", 1);
});
}
, rangedSelect = function ()
{
var items = canvasView.childNodes;
var k = indexingItem;
if(Array.prototype.indexOf.call(items, k) < Array.prototype.indexOf.call(items, canvasView.idata.stage))
{
while(k != canvasView.idata.stage)
{
k.setAttribute("selected", 1);
k = k.nextSibling;
}
}
else
{
while(k != canvasView.idata.stage)
{
k.setAttribute("selected", 1);
k = k.previousSibling;
}
}
}
, deselectAllItem = function ()
{
IDOMElement(canvasView).foreach(1, function(target)
{
target.removeAttribute("selected");
});
}
, reverseSelection = function ()
{
IDOMElement(canvasView).foreach(1, function(target)
{
target.hasAttribute("selected") ? target.removeAttribute("selected") : target.setAttribute("selected", 1);
});
}
//// ContextMenu Handlers: Collections
, setCollection = function ()
{
var s = selections( true )
var name_field = Dand.wrap(
"input", null
, "v_snippet_input_single", null
, new IKey( "type", "text" )
);
new MessageBox(
"Collection name"
, name_field
, "OK", "Cancel"
, requestCollection.bind({ name: name_field, files: s.join(",") })
).show();
}
, openCollection = function ( id ) {
refreshCanvas( id, true );
}
, excludeCollection = function() {
}
, insertCollection = function() {
var collections = []
, ul = Dand.wrapc( "canvasGeneral asl_colls" )
;
// Get current albums to list
IDOMElement(canvasView).foreach(1, function(target)
{
if(target.hasAttribute("collection"))
{
var t = IDOMElement(target)
// item structure
, li = Dand.wrap(
null, "g_item" + Perf.uuid, null
, [
Dand.wrap("span", null, "c75", t.getDAttribute("title") )
, Dand.wrap("span", null, "c25", t.getDAttribute("author") )
]
, new DataKey("id", t.getDAttribute("id"))
);
// Set selection behaviour
IDOMElement(li).addEventListener("Click", function(e) {
IDOMElement(ul).foreach(1, function(elem) { elem.hasAttribute("selected") && elem.removeAttribute("selected"); });
this.setAttribute("selected", 1);
}.bind(li));
ul.appendChild(li);
}
});
new MessageBox("Select a collection", ul, "OK", "Cancel", requestInsert.bind({ albumList: ul, collection: selections(true) })).show();
}
//// ContextMenu Handlers: General actions
, requestRename = function( confirmed )
{
if( confirmed )
{
var pData = {
"name": this.name.value
, "id": IDOMElement( this.stage ).getDAttribute( "id" )
};
if(this.isCollection) pData.group = "rename";
else pData.file = "rename";
postData( processorSet, pData, refreshCanvas, loadFailed );
}
}
, requestDelete = function (confirmed)
{
if(confirmed || this.reConfirmed)
{
if(this.files.length < 2)
{
var file = this.files[0];
if(selHasCollection)
{
new MessageBox("Also delete files?"
, "Do you also want to delete the files within the collections?"
, "Delete all files", "Only delete collection"
, delCollection.bind(file)).show();
}
else
{
postData(
processorSet
, { "file": "remove", "hash": IDOMElement(file).getDAttribute("hash") }
, fileDeleted.bind(file), loadFailed
);
}
}
else
{
if(!this.reConfirmed && selHasCollection)
{
// Set the reconfirmation attr
this.reConfirmed = true;
new MessageBox("Also delete files?"
, "You have also selected collection(s), do you want to also delete files inside?"
, "Delete all files", "Only delete collection"
, requestDelete.bind(this)).show();
return;
}
var files = this.files;
for(var i in files)
{
if(files[i].hasAttribute("collection"))
{
// redirect confirmation to delCollection handler
// delete all things when true
delCollection.bind(files[i])(confirmed);
}
else
{
// redirect to self
requestDelete.bind({files: [files[i]]})(true);
}
}
}
}
}
, requestInsert = function(confirmed)
{
if( confirmed )
{
var selectedAlbum = IDOMElement(
IDOMElement( this.albumList ).first( 1, function(elem) {
return elem.hasAttribute("selected");
} ) ).getDAttribute( "id" );
postData(
processorSet
, { "group": "insert", "id": selectedAlbum , "files": this.collection.join(",") }
, refreshCanvas, loadFailed
);
}
}
, delCollection = function (confirmed)
{
var album_id = IDOMElement(this).getDAttribute("id");
if( confirmed )
{
postData( processorGet, { group: "get", aid: album_id }, getFilestoDelete.bind( this ), loadFailed );
}
else
{
postData( processorSet, { group: "remove", id: album_id }, refreshCanvas, loadFailed );
}
}
, getFilestoDelete = function ( e )
{
var l = Object.keys(e.files).length
, fc = 0
, _self = this
, echoDeleted = function()
{
debug.Info("[ASL] File deleted: " + this.name);
fc ++;
if(l == fc) delCollection.bind(_self)(false);
}
, deleteFailed = function ()
{
debug.Error( new Error( "[ASL] Failed to delete: " + this.name ) );
fc ++;
if(l == fc) delCollection.bind(_self)(false);
}
;
for(var i in e.files)
{
postData(
processorSet
, { "file": "remove", "hash": e.files[i]}, echoDeleted.bind({ "name": i })
, deleteFailed.bind({ "name": i })
);
}
}
, fileDeleted = function () { this.parentNode.removeChild(this); }
, requestCollection = function ()
{
if(this.name.value)
{
postData(
processorSet
, { "group": "create", "name": this.name.value, "files": this.files }
, refreshCanvas, loadFailed
);
}
}
////// End canvas builders
, refreshCanvas = function ( view, openCollection )
{
if( typeof view != "string" && !openCollection ) view = null;
// prepare postData
/** @type {_AstJson_.AJaxGetFiles.Request} */
var pdata = {};
if( openCollection )
{
// Set and remove to prevent invalid content set to currentView
inCollection = view;
view = false;
}
currentView = view || ( currentView || "application" );
//// postData parameters
// if we are in collection
if( inCollection )
{
pdata.group = "list";
pdata.aid = inCollection;
}
// else we are in root
else pdata.listFiles = currentView;
switch( currentView )
{
case "image":
postData( processorGet, pdata, buildImageCanvas, loadFailed );
break;
case "audio":
postData( processorGet, pdata, buildAudioCanvas, loadFailed );
break;
default:
postData( processorGet, pdata, buildGeneralCanvas, loadFailed );
break;
}
}
/** @param {_AstJson_.AJaxGetFiles} e */
, panelSwitch = function ( e )
{
if( view_index.length < 1 )
{
var menuBar = Dand.id( "asl_contentMenu" )
, f = e.files, first;
// button mime/type ( counts )
for( var i in f )
{
var elem = Dand.wrap(
"span", null, "asl_menuItem"
, i + "(" + f[i] + ")"
, new DataKey( "name", i ) );
view_index[view_index.length] = [i, elem];
menuBar.appendChild(elem);
IDOMElement(elem).addEventListener(new EventKey("Click", switchView.bind(IDOMElement(elem))));
if( !first ) first = [ i, elem ];
}
if( !first )
{
debug.Info( "No files" );
return;
}
// begin load index
refreshCanvas( first[0] );
// Set style
first[1].setAttribute("current", 1);
}
else
{
// Should update the menu buttons
debug.Info( "Should update the menu buttons" );
}
}
, switchView = function ()
{
// Do nothing if current
if(this.getDAttribute("name") == currentView) return;
for(var i in view_index)
{
if(view_index[i][0] == currentView)
{
view_index[i][1].removeAttribute("current");
}
}
// switching view, reset collection
inCollection = 0;
this.setAttribute("current", 1);
refreshCanvas(this.getDAttribute("name"));
}
, showLibrary = new EventKey("Click"
, function ()
{
stage.style.top = "0";
asl_smask.setAttribute( "expand", 1 );
// Switch behaviour
stage.removeEventListener( showLibrary );
Cycle.delay(function () {
Dand.id( "ae_body" ).style.display = Dand.id( "ae_panel" ).style.display = "none";
asl_smask.addEventListener( hideLibrary );
// load library statistics
loadLibStats( panelSwitch, loadFailed );
}, 500);
}
)
, hideLibrary = new EventKey(
"Click"
, function ()
{
stage.style.top = "";
asl_smask.removeAttribute( "expand" );
// Switch behaviour
asl_smask.removeEventListener( hideLibrary );
Dand.id("ae_body").style.display = Dand.id( "ae_panel" ).style.display = "";
Cycle.delay(function () {
stage.addEventListener( showLibrary );
}, 500);
}
)
, loadFailed = function (e)
{
// TODO: make some notifications here
}
, loadLibStats = function ( handler, failedHandler )
{
postData( processorGet, { "countTypes": 1 }, handler, failedHandler );
}
, keyHold = function(e) { holdingCtrl = e.ctrlKey; holdingShift = e.shiftKey; }
, dKeyUp = new EventKey( "KeyUp", keyHold )
, dKeyDown = new EventKey( "KeyDown", keyHold )
;
Dand.id( "asl_homeBtn", true ).addEventListener( "click", function( e ) { refreshCanvas( 0, true ); } );
Dand.id( "asl_refresh", true ).addEventListener( "click", function( e ) { refreshCanvas( 0 ); } );
new IDOMObject( document ).addEventListeners([ dKeyUp, dKeyDown ]);
stage.addEventListener(showLibrary);
};
ns[ NS_EXPORT ]( EX_CLASS, "SiteLibrary", SiteLibrary );
})();

View File

@ -1,71 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.SmartInput.CandidateAction" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
var getData = __import( "System.Net.getData" );
var prettyDate = __import( "Astro.utils.Date.pretty" );
/** @type {_AstConf_.AstroEdit} */
var Conf = Config.get( "AstroEdit" );
/** @type {Astro.Blog.AstroEdit.SmartInput.ICandidateAction} */
var ArticleRefs = function ( visualizer, key )
{
this.visualizer = visualizer;
this.key = key;
this.__cands = {};
};
ArticleRefs.prototype.GetCandidates = function( handler )
{
var _self = this;
getData( Conf.paths.list_articles, function( e ) {
e = JSON.parse( e );
for( var i in e.entries )
{
var ent = e.entries[i];
_self.__cands[ ent.title ] = { "desc": ent.content, id: ent.id };
}
handler( _self.__cands );
} );
};
ArticleRefs.prototype.Process = function( key )
{
var cand = this.__cands[ key ];
if( !cand ) return false;
this.visualizer.insertSnippet( "articlelink", { value: cand.id } );
return true;
};
ArticleRefs.prototype.Retreat = function( sender, e )
{
return sender.value == "" && e.keyCode == 8; // Backspace
};
/** @type {Astro.Blog.AstroEdit.SmartInput.ICandidateAction} */
var ArticleContent = function ( visualizer, key )
{
ArticleRefs.call( this, visualizer, key );
};
__extends( ArticleContent, ArticleRefs );
ArticleContent.prototype.Process = function( key )
{
var cand = this.__cands[ key ];
if( !cand ) return false;
this.visualizer.insertSnippet( "articlecontent", { value: cand.id } );
return true;
};
ns[ NS_EXPORT ]( EX_CLASS, "ArticleContent", ArticleContent );
ns[ NS_EXPORT ]( EX_CLASS, "ArticleReference", ArticleRefs );
})();

View File

@ -1,37 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.SmartInput.CandidateAction" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Astro.Blog.AstroEdit.SmartInput.ICandidateAction} */
var Footnote = function ( visualizer, key )
{
this.visualizer = visualizer;
this.key = key;
};
Footnote.prototype.GetCandidates = function( handler )
{
handler( false );
};
Footnote.prototype.Process = function( content )
{
this.visualizer.insertSnippet( "footnote", { "value": content } );
};
Footnote.prototype.Retreat = function( sender, e )
{
return sender.value == "" && e.keyCode == 8; // Backspace
};
ns[ NS_EXPORT ]( EX_CLASS, "Footnote", Footnote );
})();

View File

@ -1,28 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.SmartInput.CandidateAction" );
/** @type {Astro.Blog.AstroEdit.SmartInput.ICandidateAction} */
var Heading = function ( visualizer, key )
{
this.visualizer = visualizer;
this.key = key;
};
Heading.prototype.GetCandidates = function( handler )
{
handler( false );
};
Heading.prototype.Process = function( content )
{
this.visualizer.insertSnippet( "heading", { "size": this.key, "value": content } );
};
Heading.prototype.Retreat = function( sender, e )
{
return sender.value == "" && e.keyCode == 8; // Backspace
};
ns[ NS_EXPORT ]( EX_CLASS, "Heading", Heading );
})();

View File

@ -1,21 +0,0 @@
.smartbar-candidates {
padding: 0.5em;
background-color: rgba( 0, 0, 0, 0.2 );
}
.smartbar-candidates .cn {
padding: 0.2em 0.5em;
}
.smartbar-candidates .cn:hover {
background-color: rgba( 0, 0, 0, 0.2 );
}
.smartbar-candidates .cn[data-selected="1"] {
background-color: orangered;
}
.cn .desc {
margin-left: 0.5em;
opacity: 0.65;
}

View File

@ -1,521 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.AstroEdit" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion.IDOMObject} */
var IDOMObject = __import( "Dandelion.IDOMObject" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
/** @type {System.Net.ClassLoader} */
var Loader = __import( "System.Net.ClassLoader" );
/** @type {System.utils} */
var utils = __import( "System.utils" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
var moduleNs = "Astro.Blog.AstroEdit.SmartInput.CandidateAction.";
var service_uri = Config.get( "ServiceUri" );
var Destructor = function( target )
{
this.target = target;
this.target.Disposed = false;
this.destructSequence = [];
};
Destructor.prototype.Register = function( destruct )
{
this.destructSequence.push( destruct );
};
Destructor.prototype.Destruct = function()
{
for( var i in this.destructSequence )
{
this.destructSequence[i]();
}
this.target.Disposed = true;
this.destructSequence = null;
};
var KeyHandler = function( sender, handler )
{
return function( e )
{
e = e || window.event;
if ( e.keyCode ) code = e.keyCode;
else if ( e.which ) code = e.which;
handler( sender, e );
};
};
// {{{ Candidates Class
var Candidates = function( title, desc, defs )
{
this.title = title;
this.desc = desc;
this.__cands = [];
this.__defs = defs || {};
this.Empty = !defs;
};
Candidates.prototype.Get = function()
{
if( this.__cands.length ) return this.__cands;
for( var i in this.__defs )
{
/** @param {Astro.Blog.AstroEdit.SmartInput.Definition} */
var c = this.__defs[i];
this.__cands.push( Dand.wrapc( "cn", [ i, Dand.wrapc( "desc", c.desc ) ], new DataKey( "key", i ) ) );
}
return this.__cands;
};
Candidates.prototype.Reset = function()
{
var Cands = this.Get();
for( var i in Cands )
{
var c = IDOMElement( Cands[i] );
c.setAttribute( new DataKey( "selected", 0 ) );
}
};
Candidates.prototype.Filtered = function()
{
var Cands = this.Get();
var selected = [];
for( var i in Cands )
{
var c = IDOMElement( Cands[i] );
c.setAttribute( new DataKey( "selected", 0 ) );
if( c.style.display != "none" )
{
selected.push( c );
}
}
return selected;
};
Candidates.prototype.Selected = function()
{
var Cands = this.Get();
for( var i in Cands )
{
var c = IDOMElement( Cands[i] );
if( c.getDAttribute( "selected" ) == "1" )
{
return c;
}
}
return null;
};
// }}}
/** @param {Astro.Blog.AstroEdit.Visualizer} */
var SmartInput = function( visualizer )
{
this.Present = false;
var destructor = new Destructor( this );
var _self = this;
var insert = function() { return Dand.textNode( "" ); };
var ModLevels = [];
var BindingBox = null;
ModLevels.Cands = function() { return ModLevels[0][0]; };
ModLevels.Action = function() { return ModLevels[0][1]; };
ModLevels.Retreat = function() { return ModLevels[0][2]; };
var __title = null;
var title = function( reload )
{
if( !reload && __title ) return __title;
var l = ModLevels.length - 1;
var t = ModLevels[ l ][0].title;
for( var i = 0; i < l; i ++ )
{
var Mod = ModLevels[i];
t = t + " > " + Mod[0].title;
}
if( __title )
{
__title.textContent = t;
}
else
{
__title = Dand.wrape( t );
}
return __title;
};
var __stage = null;
var stage = function( incoming )
{
if( __stage )
{
if( incoming )
{
IDOMElement( __stage[1] ).clear();
var ThisCands = ModLevels.Cands().Get();
if( ThisCands.length )
{
IDOMElement( __stage[1] ).loot( Dand.wrape( ThisCands ) );
}
}
return __stage;
}
var Cands = ModLevels.Cands();
var Command = Dand.wrap(
"input", null, "v_snippet_input_single"
, null, IKey.quickDef( "type", "text", "placeholder", Cands.desc, "value", "`" )
);
var CandList = Dand.wrap( "div", null, "compx smartbar-candidates", Cands.Get() );
Command.selectionStart = Command.selectionEnd = 1;
return __stage = [ Command, CandList ];
};
var CandidateCycle = -1;
var KeywordTyped = 0;
var shiftTabbed = false;
var HandleInput = function( sender, e )
{
// Don't handle if holding shift or ctrl key
if( e.shiftKey || e.ctrlKey )
{
// Except the Shift + Tab, we need to cycle this
shiftTabbed = e.shiftKey && e.keyCode == 9;
if( !shiftTabbed ) return;
}
switch( e.keyCode )
{
case 192: // `
// If we are not are the first level, do nothing
if( 1 < ModLevels.length ) break;
// Closing the quote, that means this is a block-quoted text
e.preventDefault();
insert = undefined;
// Hitting ` twice escapes the ` character itself
var v = sender.value.substr( 1 );
if( v == "" )
{
insert = function() { return Dand.textNode( "`" ); };
BindingBox.close( true );
break;
}
BindingBox.close();
// Insert the code snippet with inline flag
visualizer.insertSnippet( "code", { "inline": "on", "lang": "plain", "value": v } );
break;
case 13: // Enter
// Not closing the quote, either a direct text or the first matched action
e.preventDefault();
// No candidates, directly pass the input text to the processor
if( ModLevels.Cands().Empty && 1 < ModLevels.length )
{
ModLevels.Action()( sender.value.substr( 1 ) );
BindingBox.close();
break;
}
var selected = ModLevels.Cands().Selected();
// Check if matched an action first
if( selected )
{
insert = undefined;
var close = ModLevels.Action()( selected.getDAttribute( "key" ) );
if( close ) BindingBox.close();
}
else
{
// Insert this text directly
var v = Dand.textNode( sender.value.substr( 1 ) );
insert = function() { return v; };
BindingBox.close( true );
}
break;
case 27: // Esc
BindingBox.close();
break;
case 9: // Tab
// Hitting tab will cycle around the candidates
e.preventDefault();
var c = ModLevels.Cands().Filtered();
var l = c.length;
if( !l ) break;
CandidateCycle += e.shiftKey ? -1 : 1;
if( CandidateCycle == l )
{
CandidateCycle = 0;
}
else if( CandidateCycle == -1 )
{
CandidateCycle = c.length - 1;
}
var ThisCandidate = c[ CandidateCycle ];
ThisCandidate.setAttribute( new DataKey( "selected", 1 ) );
var CyclingKeyword = ThisCandidate.getDAttribute( "key" );
sender.value = "`" + CyclingKeyword;
// Check if only 1 matched
if( c.length == 1 && KeywordTyped == sender.value.length )
{
insert = undefined;
ModLevels.Action()( ThisCandidate.getDAttribute( "key" ) );
break;
}
sender.setSelectionRange( KeywordTyped, sender.value.length );
break;
default:
ModLevels.Cands().Filtered();
CandidateCycle = -1;
}
};
var TestEmpty = function( sender, e )
{
if( ModLevels.Retreat()( sender, e ) )
{
_self.RetreatLevel( sender );
if( !ModLevels.length ) return;
}
// Search exact matched Candidates
switch( e.keyCode )
{
case 9: // Tab, do nothing
break;
case 16: // Shift, check if shiftTabbed
if( shiftTabbed )
{
shiftTabbed = false;
break;
}
default:
if( CandidateCycle == -1 )
{
KeywordTyped = sender.value.length;
}
var c = ModLevels.Cands().Get();
var keyword = sender.value.substr( 1 );
for( var i in c )
{
var Cand = IDOMElement( c[i] );
var t = Cand.getDAttribute( "key" );
Cand.style.display = t.match( new RegExp( keyword, "i" ) ) ? "" : "none";
// Highlight the exact match
if( t.match( new RegExp( "^" + keyword + "$", "i" ) ) )
{
Cand.setAttribute( new DataKey( "selected", 1 ) );
}
}
}
};
var ClosePanel = function( confirmed )
{
visualizer.restoreSelection();
if( confirmed && insert != undefined )
visualizer.insertAtCaret( insert() );
// Posponing this prevents the BackQuoteBinding firing
Cycle.next( function() {
_self.Present = false;
destructor.Destruct();
} );
};
// Advance the input level by CandidateAction
this.advanceLevel = function( Candidates, Action, Retreat )
{
if( ModLevels.length )
{
ModLevels[0].selected = ModLevels.Cands().Selected().getDAttribute( "key" );
}
ModLevels.unshift([ Candidates, Action, Retreat ]);
if( 1 < ModLevels.length )
{
CandidateCycle = -1;
stage( Candidates );
title( true );
stage()[0].value = "`";
stage()[0].setAttribute( "placeholder", ModLevels.Cands().desc );
BindingBox.show();
}
};
this.RetreatLevel = function( sender )
{
if( ModLevels.length == 1 )
{
BindingBox.close();
destructor.Destruct();
}
ModLevels.shift();
if( ModLevels.length )
{
var Cands = ModLevels.Cands();
var input = stage( Cands )[0];
title( true );
input.value
= "`" + Cands.Selected().getDAttribute( "key" );
input.setAttribute( "placeholder", Cands.desc );
input.selectionStart = 1;
input.selectionEnd = input.value.length;
BindingBox.show();
}
};
this.Show = function()
{
if( _self.Present ) return;
visualizer.saveSelection();
_self.Present = true;
var MsgBox = new MessageBox(
title()
, Dand.wrape( stage() )
, "Back", false
, ClosePanel
);
MsgBox.show();
var Command = stage()[0];
BindingBox = MsgBox;
Command.focus();
var DCommand = IDOMElement( Command );
var KDown = KeyHandler( Command, HandleInput );
var KUp = KeyHandler( Command, TestEmpty );
DCommand.addEventListener( "KeyDown", KDown );
DCommand.addEventListener( "KeyUp", KUp );
destructor.Register( function() {
DCommand.removeEventListener( "KeyDown", KDown );
DCommand.removeEventListener( "KeyUp", KUp );
} );
};
};
var MasterInput = function( visualizer )
{
var Cands = {
"Article Reference": { module: "ArticleReference", desc: "Links to other article" }
, "Article Content": { module: "ArticleContent", desc: "Put contents of an article" }
, "facts": { module: "Facts", desc: "Facts, a fact bubble popup when mouseover" }
, "footnote": { module: "Footnote", desc: "Footnote, a footnote displayed at the end of article" }
, "h1": { module: "Heading", options: 1, desc: "Heading, size 1" }
, "h2": { module: "Heading", options: 2, desc: "Heading, size 2" }
, "h3": { module: "Heading", options: 3, desc: "Heading, size 3" }
, "h4": { module: "Heading", options: 4, desc: "Heading, size 4" }
, "h5": { module: "Heading", options: 5, desc: "Heading, size 5" }
};
var LoadModule = function( mod )
{
var ldr = new Loader( service_uri, "o" );
var ModItem = Cands[ mod ];
ldr.load( moduleNs + ModItem.module, function( e ) { ModuleLoaded( mod, e ); } );
};
var InputBox = null;
var ModuleLoaded = function( sender, e )
{
/** @type {Astro.Blog.AstroEdit.SmartInput.ICandidateAction} */
var module = new ( __import( e ) )( visualizer, sender );
var ModItem = Cands[ sender ];
module.GetCandidates( function( x ) {
InputBox.advanceLevel(
new Candidates( ModItem.module, ModItem.desc, x )
, module.Process.bind( module )
, module.Retreat.bind( module )
);
} );
};
var BackQuoteBinding = function ( sender, e )
{
if( !InputBox || InputBox.Disposed )
{
InputBox = new SmartInput( visualizer );
InputBox.advanceLevel(
// First level Candidates
new Candidates( "Quick Access", "Keyword", Cands )
, LoadModule
, function( sender, e ) { return sender.value == ""; }
);
}
if( !InputBox.Present && code == 192 )
{
e.preventDefault();
InputBox.Show();
}
};
IDOMObject( document ).addEventListener( "KeyDown", KeyHandler( document, BackQuoteBinding ), false );
};
ns[ NS_EXPORT ]( EX_CLASS, "SmartInput", MasterInput );
})();

View File

@ -1,241 +0,0 @@
(function( ){
var ns = __namespace( "Astro.Blog.AstroEdit" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
/** @type {System.utils.EventKey} */
var EventKey = __import( "System.utils.EventKey" );
/** @type {Components.Mouse.ContextMenu} */
var ContextMenu = __import( "Components.Mouse.ContextMenu" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMObject} */
var IDOMObject = __import( "Dandelion.IDOMObject" );
/** @type {Astro.Blog.Config} */
var Conf = __import( "Astro.Blog.Config" );
/** @type {System.utils.Perf} */
var Perf = __import( "System.utils.Perf" );
var postFile = __import( "System.Net.postFile" );
var Uploader = function ( set_file_uri )
{
/** @type {_AstConf_.SiteFile} */
var config = Conf.get( "SiteFile" );
// linkage
var busy = false
, placedFiles = []
, currentFile
// Prepare structure for dockpanel
, ptext = Dand.id( "asl_ptext" )
, pbar = Dand.id( "asl_pbar_fill" )
, ppreview = Dand.id( "asl_preview" )
, pfileName = Dand.id( "asl_fileName" )
, instruction = Dand.id( "asl_instruction" )
, p_status = Dand.id( "asl_u_head" )
, fileList = Dand.id( "asl_fileList" )
, stage = Dand.id( "asl_uploader" )
, uploadProgress = function(e)
{
var done = e.position || e.loaded
, total = e.totalSize || e.total
, percentage = String( Math.floor( done / total * 1000 )/10 ) + "%";
// Set progress
ptext.innetText
= ptext.textContent
= pbar.style.width
= percentage;
}
, uploadComplete = function ( response )
{
try
{
var obj = JSON.parse( response );
if(obj.status)
{
currentFile.setStatus( "ok", config.f_host + obj.destination );
}
else
{
currentFile.setStatus( "error", obj.message );
}
new ContextMenu( currentFile.stage, currentFile.menuKeys, "LMB", stage );
}
catch ( ex )
{
currentFile.setStatus( "error", ex.message );
debug.Error( ex );
}
beginUpload();
}
, beginUpload = function()
{
busy = true;
if( placedFiles.length )
{
currentFile = placedFiles.pop();
if( currentFile )
{
var file = currentFile.file;
pfileName.textContent = pfileName.innetText = file.name;
var fd = new FormData();
fd.append( "uploadFile", file );
postFile( set_file_uri, fd, { progress: uploadProgress, complete: uploadComplete } );
currentFile.setStatus("active");
instruction.style.marginTop = "-80px";
}
else
{
// deleted file, skip it
beginUpload();
}
}
else
{
busy = false;
instruction.style.marginTop = "";
}
}
, clearFileList = function ()
{
while( fileList.hasChildNodes() )
{
fileList.removeChild( fileList.firstChild );
}
}
, retryUpload = function ()
{
this.setStatus("pending");
placedFiles[placedFiles.length] = this;
new ContextMenu( this.stage, this.menuKeys, "RMB", stage );
if( !busy ) beginUpload();
}
, removeItem = function ()
{
this.stage.style.marginTop = "-2em";
this.stage.style.opacity = "0";
if( placedFiles.indexOf(this) != -1 )
{
delete placedFiles[placedFiles.indexOf(this)];
}
Cycle.delay(function () {
fileList.removeChild(this);
}.bind(this.stage), 250);
}
;
fileList.style.paddingTop = String(p_status.clientHeight) + "px";
var docDom = IDOMObject( document );
// Drag/drop handlers
docDom.addEventListener( "DragOver", function ( e )
{
e.preventDefault();
this.className = "dragged_over";
} );
docDom.addEventListener( "DragEnd", function () { this.className = ""; } );
docDom.addEventListener( "Drop", function ( e )
{
e.preventDefault();
this.className = "";
// Push files
var list = e.dataTransfer.files;
for(var i in list)
{
if(list[i].type != undefined)
{
var fileItem = new ASLFileItem(list[i], {clear: clearFileList, remove: removeItem, retry: retryUpload});
placedFiles[placedFiles.length] = fileItem;
fileList.appendChild(fileItem.stage);
new ContextMenu(fileItem.stage, fileItem.menuKeys, "LMB", stage);
}
}
if(!busy) beginUpload();
return false;
} );
};
var ASLFileItem = function (file, callbacks)
{
var statusblob = Dand.wrap("span", null, "asl_uItemStat", "\u25CF")
, msg
, _items = [
new EventKey("Remove this item", callbacks.remove.bind(this)) // Reserved for remove item
, null // Reserved for retry/ Open link
, null // Reserved for get Error message
, new EventKey("Clear all", callbacks.clear)
]
, popMessage = function ()
{
new MessageBox("Upload error", msg).show();
}
, getFileLink = function ()
{
return msg;
}
;
this.stage = Dand.wrap( null, "asl_item" + Perf.uuid, "asl_uItem", [ statusblob, Dand.textNode(file.name) ] );
this.file = file;
this.menuKeys = _items;
this.setStatus = function (st, message)
{
msg = message;
switch(st)
{
case "active":
statusblob.style.color = "cornflowerblue";
break;
case "error":
statusblob.style.color = "red";
_items[1] = new EventKey( "Retry", callbacks.retry.bind(this) );
_items[2] = new EventKey( "Whats wrong ?", popMessage );
break;
case "ok":
statusblob.style.color = "greenyellow";
_items[1] = new EventKey( "Copy file link", getFileLink );
break;
default:// pending
delete _items[1];
delete _items[2];
statusblob.style.color = "";
}
}
};
ns[ NS_EXPORT ]( EX_CLASS, "Uploader", Uploader );
})();

View File

@ -1,5 +0,0 @@
.v_boundary[data-type="AcquireLib"] > span {
background-color: #444;
color: white;
padding: 0.2em 0.5em;
}

View File

@ -1,100 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var acquirelib = function(insertSnippet, snippetWrap, createContext, override)
{
var temp, i, j
, handler = function ()
{
// Input fields
var input_text = Dand.wrap('input', null, "v_snippet_input_single", null, new IKey("type", "text"));
if (this._stage)
{
input_text.value = this._text;
}
// Popup MessageBox
new MessageBox(
"Acquire library" + ( this._stage ? " (Edit)" : "" )
, Dand.wrape([ Dand.wrapc( "v_instruction flsf", "Module" ) , input_text ])
, "OK", "Cancel"
, visualizer.bind({ text:input_text, stage: this._stage })
).show();
}
, visualizer = function (submitted, override)
{
var src = override ? override.value : this.text.value
, stage = this.stage;
if (submitted && src)
{
// Shared clause
if (!stage)
{
if (!src) return;
// Visualize component
temp = Dand.wrap(
'span', null, "flsf"
, "AcquireLib: " + src
, [ new DataKey( "value", src ) ]
);
insertSnippet(j = snippetWrap("AcquireLib", temp, false, 'span'), Boolean(override));
}
else
{
IDOMElement(stage).setAttribute( new DataKey("value", src) );
stage.removeChild(stage.firstChild);
stage.appendChild(Dand.textNode("AcquireLib: " + src));
// set temp back to stage
temp = stage;
}
i = {_text: src, _stage: temp};
// Set context menu
createContext(i, j, handler);
}
};
if (override)
{
visualizer(true, override);
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function (stage)
{
var element = IDOMElement(stage);
return "[acquirelib]" + element.getDAttribute("value") + "[/acquirelib]";
};
__static_method( acquirelib, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "AcquireLib", acquirelib );
})();

View File

@ -1,7 +0,0 @@
.v_boundary[data-type="ArticleContent"] {
color: #999;
}
.v_boundary[data-type="ArticleContent"] span.info {
color: #f15a24;
}

View File

@ -1,160 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
/** @type {System.utils.Perf} */
var Perf = __import( "System.utils.Perf" );
/** @type {Astro.utils.Date} */
var XDate = __import( "Astro.utils.Date" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var compileProp = ns[ NS_INVOKE ]( "compileProp" );
var postData = __import( "System.Net.postData" );
/** @type {_AstConf_.AstroEdit} */
var config = null;
var ArticleContent = function ( insertSnippet, snippetWrap, createContext, override )
{
config = Config.get( "AstroEdit" );
if( !config ) throw new Error( "config is not defined" );
var temp, i, j
, handler = function ()
{
// Input fields
var v_snippetInput = Dand.wrap( "input", null, "v_snippet_input_single", null, new IKey( "type", "text" ) );
if ( this._stage )
{
v_snippetInput.value = this._id;
}
// Popup MessageBox
new MessageBox(
"ArticleContent"
, Dand.wrape([
Dand.wrapc( "v_instruction", "ArticleContent id:" )
, v_snippetInput
])
, "OK", "Cancel"
, visualizer.bind({
id: v_snippetInput
, stage: this._stage
})
).show();
}
, visualizer = function ( submitted, override )
{
var id, stage = this.stage;
if( override )
{
id = unescapeStr( override.value );
}
else
{
id = this.id.value;
}
var ACInfo = [ "ArticleContent[ ", Dand.wrap( "span", null, "info", id ), " ]" ];
if ( submitted && id )
{
// Visualize component
if (!stage)
{
temp = Dand.wrapne( "span"
, ACInfo
, new DataKey( "value", id )
);
insertSnippet(
j = snippetWrap(
"ArticleContent"
, temp
, false, "span"
)
, !!override
);
}
else
{
var stg = IDOMElement( stage );
stg.clear();
stg.loot( Dand.wrape( ACInfo ) );
stg.setAttribute( new DataKey( "value", id ) );
}
i = {
_id: id
, _stage: temp
};
// Get title of this article
postData(
config.paths.get_article
, { article_id: id }
/** @param {_AstJson_.AJaxGetArticle} */
, function( e )
{
ACInfo[1].firstChild.textContent = e.entry.title;
}
, function()
{
ACInfo[1].firstChild.textContent = "ERROR";
} );
// Set context menu
createContext( i, j, handler );
}
};
if ( override )
{
visualizer( true, override );
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function ( stage )
{
stage = IDOMElement( stage );
var options = "";
var opt;
return "[articlecontent]"
+ escapeStr( stage.getDAttribute( "value" ) )
+ "[/articlecontent]";
};
__static_method( ArticleContent, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "ArticleContent", ArticleContent );
})();

View File

@ -1,9 +0,0 @@
.v_boundary[data-type="ArticleLink"]:before {
content: "[";
}
.v_boundary[data-type="ArticleLink"] {
color: #f15a24;
}
.v_boundary[data-type="ArticleLink"]:after {
content: "]";
}

View File

@ -1,176 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
/** @type {System.utils.Perf} */
var Perf = __import( "System.utils.Perf" );
/** @type {Astro.utils.Date} */
var XDate = __import( "Astro.utils.Date" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var compileProp = ns[ NS_INVOKE ]( "compileProp" );
var postData = __import( "System.Net.postData" );
/** @type {_AstConf_.AstroEdit} */
var config = null;
var ArticleLink = function ( insertSnippet, snippetWrap, createContext, override )
{
config = Config.get( "AstroEdit" );
if( !config ) throw new Error( "config is not defined" );
var temp, i, j
, handler = function ()
{
// Input fields
var v_snippetInput = Dand.wrap( "input", null, "v_snippet_input_single", null, new IKey( "type", "text" ) )
, input_title = Dand.wrap( "input", null, "v_snippet_input_single", null, new IKey( "type", "text" ) )
;
if ( this._stage )
{
v_snippetInput.value = this._id;
input_title.value = this._title;
}
// Popup MessageBox
new MessageBox(
"Link to article"
, Dand.wrape([
Dand.wrapc( "v_instruction", "Article id:" )
, v_snippetInput
, Dand.wrapc( "v_instruction", "Title override:" )
, input_title
])
, "OK", "Cancel"
, visualizer.bind({
id: v_snippetInput
, title: input_title
, stage: this._stage
})
).show();
}
, visualizer = function ( submitted, override )
{
var id, stage = this.stage;
if( override )
{
id = unescapeStr( override.value );
title = unescapeStr( override.title ) || "";
}
else
{
id = this.id.value;
title = this.title.value;
}
if ( submitted && id )
{
// Visualize component
if (!stage)
{
temp = Dand.wrapne( "span"
, title || "ArticleLink[" + id + "]"
, [
new DataKey( "value", id )
, new DataKey( "title", title )
]
);
insertSnippet(
j = snippetWrap( "ArticleLink", temp, false, "span" )
, !!override
);
}
else
{
stage.firstChild.textContent = title || "ArticleLink[" + id + "]";
IDOMElement( stage ).setAttribute([
new DataKey( "value", id )
, new DataKey( "title", title )
]);
}
// Get the default title if not defined
if( !title )
{
postData(
config.paths.get_article
, { article_id: id }
/** @param {_AstJson_.AJaxGetArticle} */
, function( e )
{
j.firstChild.textContent = e.entry.title;
}
, function()
{
j.firstChild.textContent = "ArticleLink[ ERROR ]";
} );
}
i = {
_id: id
, _title: title
, _stage: temp
};
// Set context menu
createContext( i, j, handler );
}
};
if ( override )
{
visualizer( true, override );
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function ( stage )
{
stage = IDOMElement( stage );
var options = "";
var opt;
if( opt = stage.getDAttribute( "title" ) )
{
options += " title=\"" + escapeStr( opt ) + "\"";
}
return "[articlelink" + options + "]"
+ escapeStr( stage.getDAttribute( "value" ) )
+ "[/articlelink]";
};
__static_method( ArticleLink, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "ArticleLink", ArticleLink );
})();

View File

@ -1,12 +0,0 @@
.v_boundary[data-inline="on"][data-type="Code"] {
display: inline-block;
background-color: #EEE;
}
.v_box[data-inline="on"] .v_description {
display: none;
}
.v_box[data-inline="on"] {
min-height: 0;
}

View File

@ -1,214 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var compileProp = ns[ NS_INVOKE ]( "compileProp" );
var code = function ( insertSnippet, snippetWrap, createContext, override )
{
var temp, i, j
, codeLangs = IKey.quickDef(
"Plain text" , "plain"
, "AS3" , "as3"
, "bash" , "bash"
, "C#" , "csharp"
, "C/C++" , "cpp"
, "CSS" , "css"
, "php" , "php"
, "Python" , "python"
, "Perl" , "perl"
, "Ruby" , "ruby"
, "Html/Xml" , "xml"
, "Java" , "java"
, "JavaScript" , "js"
, "SQL" , "sql"
)
// Private methods
, compileListItems = function ()
{
var arr = [];
for ( i in codeLangs )
{
arr[ arr.length ] = Dand.wrapne(
"option"
, codeLangs[i].keyName
, new IKey( "value", codeLangs[i].keyValue )
);
}
return arr;
}
// Snippet Class structure: handler & visualizer
, handler = function ()
{
// Input fields
var v_snippetInput = Dand.wrap( "textarea", null, "v_snippet_input" )
, v_codelang = Dand.wrap( "select", null, "v_select flsf", compileListItems() )
, input_inline = Dand.wrapna( "input", new IKey( "type", "checkbox" ) );
if ( this._stage )
{
if ( this._lang )
{
for ( i = 0; i < codeLangs.length; i ++ )
{
if ( codeLangs[i].keyValue == this._lang )
{
v_codelang.selectedIndex = i;
}
}
}
v_snippetInput.value = this._content || "";
input_inline.checked = ( this._inline == "on" );
}
else
{
// Remember the last choice
if ( typeof( this.pSnippeCodeChoice ) == "number" )
v_codelang.selectedIndex = this.pSnippeCodeChoice;
}
// Popup MessageBox
new MessageBox(
( this._stage ? "Edit" : "Insert" ) + " code snippet"
, Dand.wrapc(
"v_trimmer"
, [
Dand.wrapc( "v_instruction", v_codelang )
, v_snippetInput
, Dand.wrape( Dand.wrapne( "label", [ input_inline, "Inline" ] ) )
]
)
, "OK", "Cancel"
// Switcher
, visualizer.bind({ code:v_snippetInput, inline: input_inline, lang: v_codelang, stage: this._stage })
).show();
}
/* @type override {_AstXObject_.AstroEdit.Visualizer.Snippet.Code.Override} */
, visualizer = function( submitted, override )
{
var lang, code, inline
, stage = this.stage;
if( override )
{
lang = unescapeStr( override.lang );
code = unescapeStr( override.value );
inline = override.inline;
}
else
{
lang = this.lang[this.pSnippeCodeChoice = this.lang.selectedIndex].value;
code = this.code.value;
inline = this.inline.checked ? "on" : "";
}
var langName;
for( var i in codeLangs )
{
if( codeLangs[i].keyValue == lang )
{
langName = codeLangs[i].keyName;
break;
}
}
if ( submitted && code )
{
if ( !stage )
{
// Visualize component
temp = Dand.wrapc(
"v_box"
, [
Dand.wrapne( "pre", code )
, Dand.wrapc( "v_description", "Script language: " + langName )
]
, [
new DataKey( "value", code )
, new DataKey( "lang", lang )
, new DataKey( "inline", inline )
]
);
insertSnippet( j = snippetWrap( "Code", temp ), Boolean( override ) );
}
else
{
IDOMElement( stage ).setAttribute(
[
new DataKey( "value", code )
, new DataKey( "lang", lang )
, new DataKey( "inline", inline )
]
);
temp = stage.firstChild;
temp.removeChild( temp.firstChild );
stage.firstChild.appendChild( Dand.textNode( code ) );
temp = stage.lastChild;
temp.removeChild( temp.firstChild );
temp.appendChild( Dand.textNode( "Script language: " + langName ) );
temp = stage;
}
i = { _inline: inline, _lang: lang, _content: code, _stage: temp };
// Set the inline style
IDOMElement( j ).setAttribute( new DataKey( "inline", inline ) );
// Set context menu
createContext( i, j, handler );
}
}
;
if ( override )
{
visualizer( true, override );
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function ( stage )
{
// [code lang=\"" + lang + "\"]" + code + "[/code]"
var element = IDOMElement( stage )
, props= [ "lang", "inline" ];
return "[code"
+ compileProp( element, props )
+ "]"
+ escapeStr( element.getDAttribute( "value" ) )
+ "[/code]"
;
};
__static_method( code, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "Code", code );
})();

View File

@ -1,3 +0,0 @@
.v_boundary[data-type="Footnote"] {
color: #f15a24;
}

View File

@ -1,98 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var footnote = function( insertSnippet, snippetWrap, createContext, override )
{
var temp, i, j
, handler = function ()
{
// Input fields
var v_snippetInput = Dand.wrap( "textarea", null, "v_snippet_input" );
if ( this._stage )
{
v_snippetInput.value = this._mText;
}
// Popup MessageBox
new MessageBox(
"Insert Footnote"
, v_snippetInput
, "OK", "Cancel"
, visualizer.bind({ mText: v_snippetInput, stage: this._stage })
).show();
}
, visualizer = function( submitted, override )
{
var mText, stage = this.stage;
mText = override ? unescapeStr( override.value ) : this.mText.value;
if (submitted && mText)
{
if (!stage)
{
// Visualize component
temp = Dand.wrapne( "span", "^", [
new DataKey( "value", mText )
]);
insertSnippet(
j = snippetWrap( "Footnote", temp, false, "span" )
, Boolean( override )
);
}
else
{
IDOMElement( stage ).setAttribute(new DataKey( "value", mText ));
temp = stage;
}
i = { _mText: mText, _stage: temp };
// Set context menu
createContext( i, j, handler );
}
};
if ( override )
{
visualizer( true, override );
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function (stage)
{
// [footnote][/footnote]
return "[footnote]" + escapeStr( IDOMElement(stage).getDAttribute("value") ) + "[/footnote]";
};
__static_method( footnote, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "Footnote", footnote );
})();

View File

@ -1,178 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var compileProp = ns[ NS_INVOKE ]( "compileProp" );
var heading = function ( insertSnippet, snippetWrap, createContext, override )
{
var temp, i, j
, Sizes = IKey.quickDef(
"h1", "h1"
, "h2", "h2"
, "h3", "h3"
, "h4", "h4"
, "h5", "h5"
)
// Private methods
, compileListItems = function ()
{
var arr = [];
for ( i in Sizes )
{
arr[ arr.length ] = Dand.wrapne(
"option"
, Sizes[i].keyName
, new IKey( "value", Sizes[i].keyValue )
);
}
return arr;
}
// Snippet Class structure: handler & visualizer
, handler = function ()
{
// Input fields
var v_snippetInput = Dand.wrap('input', null, "v_snippet_input_single", null, new IKey("type", "text") )
, v_headingsize = Dand.wrap( "select", null, "v_select flsf", compileListItems() );
if ( this._stage )
{
if ( this._size )
{
for ( i = 0; i < Sizes.length; i ++ )
{
if ( Sizes[i].keyValue == this._size )
{
v_headingsize.selectedIndex = i;
}
}
}
v_snippetInput.value = this._content || "";
}
else
{
// Remember the last choice
if ( typeof( this.pSnippeHeadingChoice ) == "number" )
v_headingsize.selectedIndex = this.pSnippeHeadingChoice;
}
// Popup MessageBox
new MessageBox(
( this._stage ? "Edit" : "Insert" ) + " heading text"
, Dand.wrapc(
"v_trimmer"
, [
v_snippetInput
, Dand.wrapc( "v_instruction", v_headingsize )
]
)
, "OK", "Cancel"
// Switcher
, visualizer.bind({ heading:v_snippetInput, size: v_headingsize, stage: this._stage })
).show();
}
, visualizer = function ( submitted, override )
{
var size, heading
, stage = this.stage;
if ( override )
{
size = unescapeStr( override.size );
heading = unescapeStr( override.value );
}
else
{
size = this.size[this.pSnippeHeadingChoice = this.size.selectedIndex].value;
heading = this.heading.value;
}
var size;
for( var i in Sizes )
{
if( Sizes[i].keyValue == size )
{
size = Sizes[i].keyName;
break;
}
}
if ( submitted && heading )
{
if ( !stage )
{
// Visualize component
temp = Dand.wrapne( "span", Dand.wrapne( size, heading ), [
new DataKey( "value", heading )
, new DataKey( "size", size )
]);
insertSnippet( j = snippetWrap( "Heading", temp ), Boolean( override ) );
}
else
{
IDOMElement( stage ).setAttribute([
new DataKey( "value", heading )
, new DataKey( "size", size )
]);
stage.removeChild( stage.firstChild );
stage.appendChild( Dand.wrapne( size, heading ) );
temp = stage;
}
i = { _size: size, _content: heading, _stage: temp };
// Set context menu
createContext( i, j, handler );
}
}
;
if ( override )
{
visualizer( true, override );
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function ( stage )
{
var element = IDOMElement( stage )
, props = [ "size" ];
return "[heading"
+ compileProp( element, props )
+ "]"
+ escapeStr( element.getDAttribute( "value" ) )
+ "[/heading]"
;
};
__static_method( heading, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "Heading", heading );
})();

View File

@ -1,107 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var html = function( insertSnippet, snippetWrap, createContext, override )
{
var temp, i, j
, handler = function ()
{
// Input fields
var v_snippetInput = Dand.wrap( "textarea", null, "v_snippet_input" );
if ( this._stage )
{
v_snippetInput.value = this._code;
}
// Popup MessageBox
new MessageBox(
"Insert Html snippet"
, v_snippetInput
, "OK", "Cancel"
, visualizer.bind({ code: v_snippetInput, stage: this._stage })
).show();
}
, visualizer = function( submitted, override )
{
var code, stage = this.stage;
code = override ? unescapeStr( override.value ) : this.code.value;
if (submitted && code)
{
if (!stage)
{
// Visualize component
temp = Dand.wrapc(
"v_box"
, [
Dand.wrapne( "pre", code )
, Dand.wrapc( "v_description", "Raw Html Codes" )
]
, [
new DataKey( "value", code )
, new IKey( "style", "max-height: 150px;" )
]
);
insertSnippet(j = snippetWrap("Html", temp), Boolean(override));
}
else
{
IDOMElement( stage ).setAttribute(new DataKey( "value", code ));
temp = stage.firstChild;
temp.removeChild(temp.firstChild);
stage.firstChild.appendChild(Dand.textNode( code ));
temp = stage;
}
i = { _code: code, _stage: temp };
// Set context menu
createContext( i, j, handler );
}
};
if ( override )
{
visualizer( true, override );
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function (stage)
{
// [html][/html]
return "[html]" + escapeStr( IDOMElement(stage).getDAttribute("value") ) + "[/html]";
};
__static_method( html, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "Html", html );
})();

View File

@ -1,173 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var compileProp = ns[ NS_INVOKE ]( "compileProp" );
var image = function( insertSnippet, snippetWrap, createContext, override )
{
var temp, i, j
, handler = function ()
{
// Input fields
var input_url = Dand.wrap(
"input", null, "v_snippet_input_single", null, new IKey( "type", "text" )
)
, input_a = Dand.wrap(
"input", null, "v_snippet_input_single", null, new IKey( "type", "text" )
)
, input_preferred = Dand.wrapna( "input", new IKey( "type", "checkbox" ) )
;
if ( this._stage )
{
input_url.value = this._url;
input_a.value = this._href;
input_preferred.checked = ( this._preferred == "on" );
}
// Popup MessageBox
new MessageBox(
( this._stage ? "Edit" : "Insert" ) + " image snippet",
Dand.wrape([
Dand.wrapc( "v_instruction flsf", "Link to the image:" )
, input_url
, Dand.wrapc( "v_instruction flsf", "Ancohr link(optional):" )
, input_a
, Dand.wrape( Dand.wrapne( "label", [ input_preferred, "Preferred" ] ) )
]
)
, "OK", "Cancel"
, visualizer.bind({ url:input_url, href:input_a, stage: this._stage, preferred: input_preferred })
).show();
}
, visualizer = function ( submitted, override )
{
var src, href, preferred
, stage = this.stage;
if ( override )
{
src = unescapeStr( override.value );
href = unescapeStr( override.href );
preferred = override.preferred ? "on" : "";
}
else
{
src = this.url.value;
href = this.href.value;
preferred = this.preferred.checked ? "on" : "";
}
if ( submitted && src )
{
// Shared clause
i = Dand.textNode(href ? ("link to: " + href): "No link");
if ( !stage )
{
if ( !src ) return;
// Visualize component
temp = Dand.wrapc(
"v_box"
, [
Dand.wrapna(
"img"
, [
new IKey( "src", src )
, new IKey( "style", "max-width: 100%" )
]
)
// caption
, Dand.wrapc( "v_description", i )
]
, [
new DataKey( "value", src )
, new DataKey( "href", href )
, new DataKey( "preferred", preferred )
]
);
insertSnippet( j = snippetWrap( "Image", temp ), Boolean( override ) );
}
else
{
IDOMElement( stage ).setAttribute
([
new DataKey( "value", src )
, new DataKey( "href", href )
, new DataKey( "preferred", preferred )
]);
stage.firstChild.setAttribute("src", src);
temp = stage.lastChild;
temp.removeChild(temp.firstChild);
temp.appendChild(i);
// set temp back to stage
temp = stage;
}
i = {
_url: src
, _href: href
, _preferred: preferred || "off"
, _stage: temp
};
// Set context menu
createContext( i, j, handler );
}
}
;
if ( override )
{
visualizer( true, override );
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function ( stage )
{
// [img href=\"" + this.href.value + "\"]" + this.url.value + "[/img]
var element = IDOMElement( stage )
, props = [ "href", "preferred" ]
return "[img" + compileProp( element, props ) + "]"
+ escapeStr( element.getDAttribute( "value" ) )
+ "[/img]"
;
};
// Alias
var alias = "img";
__static_method( image, "compile", compile );
__const( image, "alias", alias );
ns[ NS_EXPORT ]( EX_CLASS, "Image", image );
})();

View File

@ -1,3 +0,0 @@
.v_boundary[data-type="Link"] {
color: #f15a24;
}

View File

@ -1,132 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var link = function(insertSnippet, snippetWrap, createContext, override)
{
var temp, i, j
, handler = function ()
{
// Input fields
var input_text = Dand.wrap("input", null, "v_snippet_input_single", null, new IKey("type", "text"))
, input_a = Dand.wrap("input", null, "v_snippet_input_single", null, new IKey("type", "text"));
if (this._stage)
{
input_text.value = this._text;
input_a.value = this._href;
}
// Popup MessageBox
new MessageBox(
(this._stage ? "Edit" : "Insert") + " link",
Dand.wrape([
Dand.wrapc("v_instruction flsf", "Text")
, input_text
, Dand.wrapc("v_instruction flsf", "Link to:")
, input_a
])
, "OK", "Cancel", visualizer.bind({text:input_text, href:input_a, stage: this._stage})).show();
}
, visualizer = function (submitted, override)
{
var src, href
, stage = this.stage;
if( override )
{
src = unescapeStr( override.value );
href = unescapeStr( override.href );
}
else
{
src = this.text.value;
href = this.href.value;
}
if (submitted && src && href)
{
// Shared clause
if (!stage)
{
if (!src) return;
// Visualize component
temp =
Dand.wrapne("span", src
, [
new DataKey("value", src)
, new DataKey("href", href)
]
);
insertSnippet(j = snippetWrap("Link", temp, false, "span"), Boolean(override));
}
else
{
IDOMElement(stage).setAttribute
(
[
new DataKey("value", src)
, new DataKey("href", href)
]
);
stage.removeChild(stage.firstChild);
stage.appendChild(Dand.textNode(src));
// set temp back to stage
temp = stage;
}
i = {_text: src, _href: href, _stage: temp};
// Set context menu
createContext(i, j, handler);
}
};
if (override)
{
visualizer(true, override);
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function (stage)
{
// [link href=\"" + this.href.value + "\"]" + text + "[/link]
var element = IDOMElement(stage)
, href = escapeStr( element.getDAttribute("href") )
, val = escapeStr( element.getDAttribute("value") ) ;
return "[link" + (href ? (" href=\"" + href + "\"") : "") + "]" + val + "[/link]";
};
__static_method( link, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "Link", link );
})();

View File

@ -1,5 +0,0 @@
.v_boundary[data-type="Meta"] > span {
background-color: #444;
color: white;
padding: 0.2em 0.5em;
}

View File

@ -1,94 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var meta = function( insertSnippet, snippetWrap, createContext, override )
{
var temp, i, j
, handler = function ()
{
// Input fields
var v_snippetInput = Dand.wrap( "textarea", null, "v_snippet_input" );
if ( this._stage )
{
v_snippetInput.value = this._code;
}
// Popup MessageBox
new MessageBox(
"Insert Meta Tags"
, v_snippetInput
, "OK", "Cancel"
, visualizer.bind({ code: v_snippetInput, stage: this._stage })
).show();
}
, visualizer = function( submitted, override )
{
var code, stage = this.stage;
code = override ? unescapeStr( override.value ) : this.code.value;
if (submitted && code)
{
if (!stage)
{
// Visualize component
temp = Dand.wrap(
'span', null, "flsf"
, "Meta Tags"
, [ new DataKey( "value", code ) ]
);
insertSnippet(j = snippetWrap( "Meta", temp, false, "span" ), Boolean(override));
}
else
{
IDOMElement( stage ).setAttribute(new DataKey( "value", code ));
temp = stage;
}
i = { _code: code, _stage: temp };
// Set context menu
createContext( i, j, handler );
}
};
if ( override )
{
visualizer( true, override );
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function (stage)
{
return "[meta]" + escapeStr( IDOMElement(stage).getDAttribute("value") ) + "[/meta]";
};
__static_method( meta, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "Meta", meta );
})();

View File

@ -1,5 +0,0 @@
.v_boundary[data-type="RespH"] > span {
background-color: #444;
color: white;
padding: 0.2em 0.5em;
}

View File

@ -1,99 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var resph = function( insertSnippet, snippetWrap, createContext, override )
{
var temp, i, j
, handler = function ()
{
// Input fields
var v_snippetInput = Dand.wrap( "textarea", null, "v_snippet_input" );
if ( this._stage )
{
v_snippetInput.value = this._code;
}
// Popup MessageBox
new MessageBox(
"Insert Response Headers"
, v_snippetInput
, "OK", "Cancel"
, visualizer.bind({ code: v_snippetInput, stage: this._stage })
).show();
}
, visualizer = function( submitted, override )
{
var code, stage = this.stage;
code = override ? unescapeStr( override.value ) : this.code.value;
if (submitted && code)
{
if (!stage)
{
// Visualize component
temp = Dand.wrap(
'span', null, "flsf"
, "Response Headers"
, [
new DataKey( "value", code )
, new IKey(
"style", "background-color: #444; color: white; padding: 0.2em 0.5em;"
)
]
);
insertSnippet(j = snippetWrap( "RespH", temp, false, "span" ), Boolean(override));
}
else
{
IDOMElement( stage ).setAttribute(new DataKey( "value", code ));
temp = stage;
}
i = { _code: code, _stage: temp };
// Set context menu
createContext( i, j, handler );
}
};
if ( override )
{
visualizer( true, override );
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function (stage)
{
return "[resph]" + escapeStr( IDOMElement(stage).getDAttribute("value") ) + "[/resph]";
};
__static_method( resph, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "RespH", resph );
})();

View File

@ -1,3 +0,0 @@
.v_box.sf-view {
max-height: 150px;
}

View File

@ -1,289 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
/** @type {System.utils.Perf} */
var Perf = __import( "System.utils.Perf" );
/** @type {System.Cycle.Trigger} */
var Trigger = __import( "System.Cycle.Trigger" );
/** @type {Astro.utils.Date} */
var XDate = __import( "Astro.utils.Date" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var compileProp = ns[ NS_INVOKE ]( "compileProp" );
var getData = __import( "System.Net.getData" );
/** @type {_AstConf_.SiteFile} */
var config = null;
var sitefile = function ( insertSnippet, snippetWrap, createContext, override )
{
config = Config.get( "SiteFile" );
if( !config ) throw new Error( "config is not defined" );
var temp, i, j
, handler = function ()
{
// Input fields
var v_snippetInput = Dand.wrap("input", null, "v_snippet_input_single", null, new IKey("type", "text"))
, input_preferred = Dand.wrapna( "input", new IKey( "type", "checkbox" ) )
;
if ( this._stage )
{
v_snippetInput.value = this._content;
input_preferred.checked = ( this._preferred == "on" );
}
// Popup MessageBox
new MessageBox(
"Insert site file"
, Dand.wrape([
v_snippetInput
, Dand.wrape( Dand.wrapne( "label", [ input_preferred, "Preferred" ] ) )
])
, "OK", "Cancel"
, visualizer.bind({
code: v_snippetInput
, input_preferred: input_preferred
, stage: this._stage
})
).show();
}
, __applyData = function (e)
{
if( typeof( e ) == "string" )
e = JSON.parse(e);
var _stage = IDOMElement( this.stage );
var isAlbum = false;
// Check if this is an album
if( isAlbum = ( "files" in e ) )
{
e.file = e.files[0];
_stage.setAttribute( new DataKey( "collection", 1 ) );
}
var s, m, l, o;
var finfo = e.file;
var content = this.stage.firstChild;
var desc = this.stage.lastChild;
var _hash = finfo.hash;
switch ( finfo.type )
{
case "image":
this.stage.removeChild(content);
// Default size is large
var _image = Dand.wrapna( "img", new IKey("src", config.path.image.large + _hash + ".jpg") );
var keys = [ new IKey( "type", "radio" ), new IKey( "name", "size_grp" + Perf.uuid ) ];
var sid;
var detectImageChange = function() { return _image.complete; };
var setImageSizeProp = function()
{
_stage.setAttribute( new DataKey( "dimensions", _image.naturalWidth + "x" + _image.naturalHeight ) );
};
var selectionChanged = function ()
{
_stage.setAttribute( new DataKey( "size", this.size ) );
//// Handles the size selection
switch(this.size)
{
case "small":
_image.setAttribute( "src", config.path.image.small + _hash + ".jpg" );
break;
case "medium":
_image.setAttribute( "src", config.path.image.medium + _hash + ".jpg" );
break;
case "large":
_image.setAttribute( "src", config.path.image.large + _hash + ".jpg" );
break;
case "original":
_image.setAttribute( "src", config.path.image.original + _hash + ".jpg" );
break;
}
Trigger.register( detectImageChange, setImageSizeProp, 100 );
};
Trigger.register( detectImageChange, setImageSizeProp, 100 );
this.stage.insertBefore( _image, desc );
desc.removeChild( desc.firstChild );
desc.appendChild(
Dand.wrape([
Dand.textNode( ( isAlbum ? "[Album] " : "" ) + "Size: ")
, s = Dand.wrapna("input", keys.concat( new IKey("id", sid = "size_" + Perf.uuid) ))
, Dand.wrapne("label", "small", new IKey("for", sid))
, m = Dand.wrapna("input", keys.concat( new IKey("id", sid = "size_" + Perf.uuid) ))
, Dand.wrapne("label", "medium", new IKey("for", sid))
, l = Dand.wrapna("input", keys.concat( new IKey("checked", "1"), new IKey("id", sid = "size_" + Perf.uuid) ))
, Dand.wrapne("label", "large (default)", new IKey("for", sid))
, o = Dand.wrapna("input", keys.concat( new IKey("id", sid = "size_" + Perf.uuid) ))
, Dand.wrapne("label", "original", new IKey("for", sid))
])
);
// ad handlers to handles size change event
IDOMElement(s).addEventListener("Change", selectionChanged.bind({size: "small"}));
IDOMElement(m).addEventListener("Change", selectionChanged.bind({size: "medium"}));
IDOMElement(l).addEventListener("Change", selectionChanged.bind({size: "large"}));
IDOMElement(o).addEventListener("Change", selectionChanged.bind({size: "original"}));
var hasValue = _stage.getDAttribute( "size" );
if( hasValue )
{
switch( hasValue )
{
case "small": s.checked = 1; break;
case "medium": m.checked = 1; break;
case "large": l.checked = 1; break;
case "original": o.checked = 1; break;
}
selectionChanged.bind({ size: hasValue })();
}
break;
case "audio":
// TODO
break;
default:
content.firstChild.nodeValue = "Regular file: " + finfo.name;
content.style.paddingBottom = "2em";
content.appendChild( Dand.wrap( "br" ) );
content.appendChild( Dand.textNode( "Date: " + XDate.pretty( new Date( finfo.date_created ), true ) ) );
}
}
, loadFailed = function (e) { }
, visualizer = function ( submitted, override )
{
var hash, _obj, stage = this.stage;
if( override )
{
hash = override.value;
preferred = override[ "preferred" ] ? "on" : "";
}
else
{
hash = this.code.value;
preferred = this.input_preferred.checked ? "on" : "";
}
_obj = { file: hash };
if ( submitted && hash )
{
// Visualize component
if (!stage)
{
temp = Dand.wrapc("v_box sf-view"
, [
Dand.wrape("Getting information from Server ...")
, Dand.wrapc("v_description", "Site file (hash): " + hash)
]
, [
new DataKey( "value", hash )
, new DataKey( "size", ( override && override.size ) || "large" )
, new DataKey( "preferred", preferred )
]
);
// Get data from site library
getData( config.path.info + hash, __applyData.bind({stage: temp, hash: hash}), loadFailed );
insertSnippet(
j = snippetWrap( "SiteFile", temp )
, !!override
);
}
else
{
IDOMElement( stage ).setAttribute([
new DataKey( "value", hash )
, new DataKey( "preferred", preferred )
]);
getData( config.path.info + hash, __applyData.bind({stage: temp, hash: hash}), loadFailed );
}
i = {
_content: hash
, _preferred: preferred || "off"
, _stage: temp
};
// Set context menu
createContext( i, j, handler );
}
};
if (override)
{
visualizer(true, override);
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function ( stage )
{
stage = IDOMElement( stage );
var options = "";
var opt;
if( opt = stage.getDAttribute( "collection" ) )
{
options += " collection=\"1\"";
}
if( opt = stage.getDAttribute( "size" ) )
{
options += " size=\"" + opt + "\"";
}
if( opt = stage.getDAttribute( "dimensions" ) )
{
options += " dimensions=\"" + opt + "\"";
}
if( opt = stage.getDAttribute( "preferred" ) )
{
options += " preferred=\"" + opt + "\"";
}
return "[sitefile" + options + "]"
+ escapeStr( stage.getDAttribute( "value" ) )
+ "[/sitefile]";
};
__static_method( sitefile, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "SiteFile", sitefile );
})();

View File

@ -1,146 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var compileProp = ns[ NS_INVOKE ]( "compileProp" );
var sound = function (insertSnippet, snippetWrap, createContext, override)
{
var temp, i, j
, defaultArt = "/assets/blog/layout-images/disc_s.png"
, handler = function ()
{
// Input fields
var input_url = Dand.wrap('input', null, "v_snippet_input_single", null, new IKey("type", "text"))
, input_albumArt = Dand.wrap('input', null, "v_snippet_input_single", null, new IKey("type", "text"))
, input_lrc = Dand.wrap('input', null, "v_snippet_input_single", null, new IKey("type", "text"))
;
if (this._stage)
{
input_url.value = this._url;
input_albumArt.value = this._albumArt;
input_lrc.value = this._lrc;
}
new MessageBox(
(this._stage ? "Edit" : "Insert") + " sound snippet"
, Dand.wrape([
Dand.wrapc("v_instruction flsf", "Link to sound:")
, input_url
, Dand.wrapc("v_instruction flsf", "Link to album art(optional):")
, input_albumArt
, Dand.wrapc("v_instruction flsf", "Link to lrc(optional):")
, input_lrc
]
)
, "OK", "Cancel", visualizer.bind({url:input_url, albumArt:input_albumArt, lrc:input_lrc, stage: this._stage})).show();
}
, visualizer = function (submitted)
{
var src, albumArt , lrc
, stage = this.stage;
if (override)
{
src = override.url;
albumArt = override.albumArt;
lrc = override.lrc;
}
else
{
src = this.url.value;
albumArt = this.albumArt.value;
lrc = this.lrc.value;
}
if (submitted && src)
{
if (!stage)
{
// Visualize component
temp = Dand.wrapc('v_box'
, [
Dand.wrape(null, new IKey
(
"style", "height: 75px; background-size: auto 75px; background-repeat: no-repeat;"
+ "background-image: url(" + (albumArt ? albumArt : defaultArt) + ")"
)
)
, Dand.wrapc('v_description', "Sound snippet")
]
, [
new DataKey("value", "")
, new DataKey("url", src)
, new DataKey("albumArt", albumArt)
, new DataKey("lrc", lrc)
]
);
insertSnippet(j = snippetWrap("Sound", temp), Boolean(override));
}
else
{
// Edit properties
stage.firstChild.style.backgroundImage = "url(" + (albumArt ? albumArt : defaultArt) + ")" ;
IDOMElement(stage).setAttribute
(
[
new DataKey("url", src)
, new DataKey("albumArt", albumArt)
, new DataKey("lrc", lrc)
]
);
}
i = {_url: src, _albumArt: albumArt, _lrc: lrc, _stage: temp};
// Set context menu
createContext(i, j, handler);
}
}
;
if (override)
{
visualizer(true, override);
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function (stage)
{
// [sound url="" albumArt="" lrc="" ][/sound]");
var element = IDOMElement(stage)
, props = ["url", "albumArt", "lrc"];
return "[sound" + compileProp( element, props ) + "][/sound]";
};
__static_method( sound, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "Sound", sound );
})();

View File

@ -1,155 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var compileProp = ns[ NS_INVOKE ]( "compileProp" );
var escapeStr = ns[ NS_INVOKE ]( "escapeStr" );
var unescapeStr = ns[ NS_INVOKE ]( "unescapeStr" );
var spoiler = function(insertSnippet, snippetWrap, createContext, override)
{
var temp, i, j
, handler = function ()
{
// Input fields
var v_snippetInput = Dand.wrap("textarea", null, "v_snippet_input")
, input_title = Dand.wrap("input", null, "v_snippet_input_single", null, new IKey("type", "text"))
, input_expanded = Dand.wrapna("input", new IKey("type", "checkbox"))
if (this._stage)
{
v_snippetInput.value = this._content;
input_title.value = this._title;
input_expanded.checked = (this._expanded == "on");
}
// Popup MessageBox
new MessageBox("Insert spoiler content"
, Dand.wrape([
Dand.wrapc("v_instruction flsf", "Title")
, input_title
, Dand.wrapc("v_instruction flsf", "Content")
, v_snippetInput
, Dand.wrape( Dand.wrapne( "label", [ input_expanded, "Expanded" ] ) )
]
)
, "OK", "Cancel", visualizer.bind({title: input_title, content:v_snippetInput, expanded: input_expanded, stage: this._stage})).show();
}
/* @type override {_AstXObject_.AstroEdit.Visualizer.Snippet.Spoiler.Override} */
, visualizer = function( submitted, override )
{
var content, title, expanded
, stage = this.stage;
if( override )
{
content = unescapeStr( override.value );
title = unescapeStr( override.title );
expanded = override.expanded ? "on" : "";
}
else
{
content = this.content.value;
title = this.title.value;
expanded = this.expanded.checked ? "on" : "";
}
if (submitted && content)
{
// Shared Clause
i = Dand.textNode(title || "Spoiler");
if (!stage)
{
if (!content) return;
// Visualize component
temp = Dand.wrapc("v_box",
[
// caption
Dand.wrapc("v_caption", i)
, Dand.textNode(content)
],
[
new DataKey("value", content)
, new DataKey("title", title)
, new DataKey("expanded", expanded)
]
);
insertSnippet(j = snippetWrap("Spoiler", temp), Boolean(override));
}
else
{
IDOMElement(stage).setAttribute
([
new DataKey("value", content)
, new DataKey("title", title)
, new DataKey("expanded", expanded)
]);
temp = stage.firstChild;
temp.removeChild(temp.firstChild);
temp.appendChild(i);
stage.removeChild(stage.lastChild);
stage.appendChild(Dand.textNode(content));
// set temp back to stage
temp = stage;
}
i = {
_title: title
, _content: content
, _expanded: expanded || "off"
, _stage: temp
};
// Set context menu
createContext(i, j, handler);
}
}
;
if (override)
{
visualizer(true, override);
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function ( stage )
{
var element = IDOMElement( stage )
, props = ["title", "expanded"];
return "[spoiler"
+ compileProp( element, props )
+ "]"
+ escapeStr( element.getDAttribute( "value" ) )
+ "[/spoiler]";
};
__static_method( spoiler, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "Spoiler", spoiler );
})();

View File

@ -1,18 +0,0 @@
.v_boundary[data-type="Video"] {
width: 640px; height: 390px;
background-color: black;
padding: 0;
}
.v_boundary[data-type="Video"] .v_box {
width: 640px; height: 390px;
position: relative;
display: table-cell;
text-align: center;
vertical-align: middle;
}
.v_boundary[data-type="Video"] .v_description {
text-align: left;
padding-left: 0.5em;
}

View File

@ -1,141 +0,0 @@
(function ()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
var getData = __import( "System.Net.getData" );
var BLANK_IMG = __import( "Dandelion.StaticRes.BLANK_IMG" );
var video = function (insertSnippet, snippetWrap, createContext, override)
{
var temp, i, j, imgSrc
, getVimeoThumbnail = function( v )
{
getData(
"//vimeo.com/api/oembed.json?url=https%3A//vimeo.com/" + v
, setThumbnail
, noThumb
);
}
, setImgSrc = function( url )
{
if( imgSrc ) imgSrc.src = url;
}
, noThumb = function () { }
, setThumbnail = function (str)
{
setImgSrc( JSON.parse(str)["thumbnail_url"] );
}
, handler = function ()
{
// Input fields
var input_url = Dand.wrap('input', null, "v_snippet_input_single", null, new IKey("type", "text"));
// Popup MessageBox
new MessageBox("Insert video snippet"
, Dand.wrape([ Dand.wrapc("v_instruction flsf", "Paste a vimeo/Youtube link below:"), input_url ])
, "OK", "Cancel", visualizer.bind(input_url)
).show();
}
, visualizer = function (submitted, override)
{
var t, v;
if (override)
{
v = override.value;
i = override.type;
}
else
{
t = this.value;
// Match youtube links
v = t.match(/\/\/(www\.)?youtube\.com\/watch\?.*?v=([^\&\?\/\#]+)/) || t.match(/\/\/(www\.)?youtube\.com\/embed\/([^\&\?\/]+)/)
|| t.match(/\/\/(www\.)?youtube\.com\/v\/([^\&\?\/]+)/) || t.match(/\/\/(www\.)?youtu\.be\/([^\&\?\/]+)/);
if (v)
{
i = "youtube";
v = v[2];
}
else
{
// match vimeo links
v = t.match(/\/\/(www\.)?vimeo.com\/(\d+)($|\/)/);
if (v)
{
i = "vimeo";
v = v[2];
}
else
{
// None matched, do nothing
return;
}
}
}
if (submitted)
{
// Visualize component
temp = Dand.wrapc('v_box'
, [
Dand.wrapc( 'v_description', i[0].toUpperCase() + i.substr(1) + ": " + v )
, imgSrc = Dand.wrapna( "img", [ new IKey( "src", BLANK_IMG ) ] )
]
, [ new DataKey("value", v), new DataKey("type", i) ]
);
if( i[0] == "v" )
{
getVimeoThumbnail( v );
}
else
{
setImgSrc( "//img.youtube.com/vi/" + v + "/hqdefault.jpg" );
}
insertSnippet(j = snippetWrap("Video", temp), Boolean(override));
// Set context menu
createContext(null, j);
}
}
if (override)
{
visualizer(true, override);
override = false;
}
else
{
return handler;
}
return true;
};
var compile = function (stage)
{
// [video type=\"youtube\"]" + v[2] + "[/video]
var element = IDOMElement(stage)
, type = element.getDAttribute("type");
return "[video type=\"" + type + "\"]" + element.getDAttribute("value") + "[/video]";
};
__static_method( video, "compile", compile );
ns[ NS_EXPORT ]( EX_CLASS, "Video", video );
})();

View File

@ -1,41 +0,0 @@
(function()
{
var ns = __namespace( "Astro.Blog.AstroEdit.Visualizer.Snippet" );
var escapeStr = function ( str )
{
if( !str ) return str;
return str
.replace( /\[/g, "&#x5B;" )
.replace( /\]/g, "&#x5D;" )
.replace( /"/g, "&quot;" )
;
};
var unescapeStr = function( str )
{
if( !str ) return str;
return str
.replace( /&#x5B;/g, "[" )
.replace( /&#x5D;/g, "]" )
.replace( /&quot;/g, "\"" )
;
};
var compileProp = function ( _iDOM, keys )
{
var i, j = "", k;
for (i in keys)
{
if( ( k = _iDOM.getDAttribute(keys[i]) ) )
{
j += " " + keys[i] + "=\"" + escapeStr( k ) + "\"";
}
}
return j;
};
ns[ NS_EXPORT ]( EX_FUNC, "escapeStr", escapeStr );
ns[ NS_EXPORT ]( EX_FUNC, "unescapeStr", unescapeStr );
ns[ NS_EXPORT ]( EX_FUNC, "compileProp", compileProp );
})();

View File

@ -1,122 +0,0 @@
.v_snippet_input {
width: 600px;
height: 350px;
}
.v_boundary {
cursor: default;
padding: 0.2em;
}
.v_box {
min-height: 3em;
overflow: hidden;
position: relative;
}
.v_caption, .v_description {
background: rgba(0, 0, 0, 0.8);
padding: 0.2em;
color: white;
width: 100%;
font-family: sans-serif;
font-size: 1em;
}
.v_caption {
position: relative;
}
.v_description {
position: absolute;
left: 0;
bottom: 0;
}
.v_caption_desc {
font-size: 60%;
}
.v_boundary:hover {
background-color: rgba(0, 0, 0, 0.2);
}
.v_snippet_input_single {
width: 600px;
margin-bottom: 0.5em;
}
textarea.v_snippet_input {
font-family: site-mono;
font-size: 1em;
}
.v_instruction {
padding: 0.2em 0;
}
.v_trimmer {
overflow: hidden;
}
.v_select {
width: 100%;
background-color: #222;
font-size: 1em;
color: white;
background-image: none;
border: none;
box-shadow: none;
-webkit-appearance: none;
}
div[data-type="token"] {
background-color: #111;
color: #EEE;
padding: 0.25em 0.5em;
margin-right: 100%;
min-width: 8em;
display: inline-block;
position: relative;
}
div[data-type="token"]:hover {
background-color: #444;
}
div[data-type="token"]:after {
content: "Loading";
position: absolute;
color: rgba( 255, 255, 255, 0.2 );
right: 0;
bottom: 0;
}
div[data-type="token"]:hover:after {
color: rgba( 255, 255, 255, 0.5 );
}
#ae_visual_snippets > span[data-name="code"] { background: white; color: cornflowerblue; }
#ae_visual_snippets > span[data-name="image"] { background: #ff0084; }
#ae_visual_snippets > span[data-name="sound"] { background: YellowGreen; }
#ae_visual_snippets > span[data-name="video"] { background: Crimson; }
#ae_visual_snippets > span[data-name="spoiler"] { background: cornflowerblue; }
#ae_visual_snippets > span[data-name="link"] { background: blue; }
#ae_visual_snippets > span[data-name="acquirelib"] { background: black; }
#ae_visual_snippets > span[data-name="html"] { background: coral; }
#ae_visual_snippets > span[data-name="sitefile"] { background: royalblue; }
#ae_visual_snippets > span[data-name="heading"] { }
#ae_visual_snippets > span[data-name="footnote"] { }
#ae_visual_snippets > span[data-name="resph"] { }
#ae_visual_snippets > span[data-name="meta"] { }
#ae_visual_snippets > span[data-name="articlelink"] { }
#ae_visual_snippets > span[data-name="articlecontent"] { }

View File

@ -1,503 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.AstroEdit" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
/** @type {System.utils} */
var utils = __import( "System.utils" );
/** @type {System.utils.Perf} */
var Perf = __import( "System.utils.Perf" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {System.utils.EventKey} */
var EventKey = __import( "System.utils.EventKey" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.Net.ClassLoader} */
var Loader = __import( "System.Net.ClassLoader" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
/** @type {Components.Mouse.ContextMenu} */
var ContextMenu = __import( "Components.Mouse.ContextMenu" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
var snippetList = [
"Code"
, "Image"
, "Sound"
, "Video"
, "Spoiler"
, "Link"
, "AcquireLib"
, "Html"
, "SiteFile"
, "Heading"
, "Footnote"
, "RespH"
, "Meta"
, "ArticleLink"
, "ArticleContent"
];
var snippetNs = "Astro.Blog.AstroEdit.Visualizer.Snippet.";
//// Document Visualizer visualize snippets, used in AstroEdit and comments
var Visualizer = function ( e_document, snippetControls, service_uri )
{
var Article = ns[ NS_INVOKE ]( "Article" );
var loadedModule = {};
//// Constants
var article;
// "[^]" does not work in IE
var stackMatch = /\[([a-z][0-9a-z]*?)([\s\S]*?)\]([\s\S]*?)\[\/\1\]/ig;
var typeMatch = /([a-z][0-9a-z]*)\=\"([^"]+)\"/ig;
var snippetTokenQueue = {};
if ( e_document instanceof Article )
{
article = e_document;
// Allow Html snippet
}
else if ( e_document instanceof CeDocument )
{
article = e_document;
}
else return;
////// Variables
var contentDiv = Dand.wrap()
var selRange;
var snippetExists = false;
var lastOffset = 0;
var raw;
///// private methods
var snippetWrap = function( snippetType, element, editable, _with )
{
var snippet = Dand.wrap(
_with || "div"
, Perf.uuid
, "comp v_boundary"
, element
, [
new IKey( "contentEditable", editable ? "true" : "false" )
, new DataKey( "type", snippetType )
]
);
return snippet;
};
var appendLinebreak = function ()
{
this.parentNode.insertBefore(Dand.wrap("br"), this.nextSibling);
}
var insertLinebreak = function ()
{
this.parentNode.insertBefore(Dand.wrap("br"), this);
};
var snippetDelete = function ()
{
this.parentNode.removeChild(this);
};
var snippetBBCode = function()
{
var snippet = IDOMElement( this );
var type = snippet.getDAttribute( "type" ).toLowerCase();
/** @type {Astro.Blog.AstroEdit.Visualizer.Snippet.Model} */
var module = loadedModule[ type ];
var title = "An error occurred";
var message = "No such module";
if( module )
{
title = "BBCode for Snippet: " + type;
message = module.compile( this.firstChild );
}
new MessageBox( title, Dand.wrapne( "pre", message ) ).show();
};
var createSnippetMenu = function ( snippetProp, snippet, editHandler, snippetActions )
{
var contextItems = [
editHandler && new EventKey( "Edit", editHandler.bind( snippetProp ) )
, new EventKey( "Insert a linebreak", insertLinebreak.bind( snippet ) )
, new EventKey( "Append a linebreak", appendLinebreak.bind( snippet ) )
, new EventKey( "Delete", snippetDelete.bind( snippet ) )
, new EventKey( "View BBCode", snippetBBCode.bind( snippet ) )
];
e_document.updateContent();
if ( snippetActions instanceof Array )
{
contextItems = snippetActions.concat( contextItems );
}
return new ContextMenu( snippet, contextItems, "RMB" );
};
var _savSelection = function ()
{
contentDiv.focus();
if ( window.getSelection )
{
var sel = window.getSelection();
if ( sel.getRangeAt && sel.rangeCount )
{
selRange = sel.getRangeAt(0);
}
}
else if ( document.selection && document.selection.createRange )
{
selRange = document.selection.createRange();
}
else
{
selRange = null;
}
};
var _resSelection = function ()
{
contentDiv.focus();
if ( selRange )
{
if ( window.getSelection )
{
var sel = window.getSelection();
sel.removeAllRanges();
sel.addRange( selRange );
}
else if ( document.selection && selRange.select )
{
selRange.select();
}
}
};
var lastLine = Dand.wrap( "br", "v_linebreak" );
var ensureLastLinebreak = function ()
{
if( !Dand.id( "v_linebreak" ) )
{
insertElement( lastLine, true );
}
else
{
insertElement( contentDiv.removeChild( lastLine ), true );
}
};
var insertAtCaret = function( element, newLine )
{
var sel, range;
if( newLine == undefined ) newLine = true;
sel = window.getSelection();
if ( sel.getRangeAt && sel.rangeCount )
{
range = sel.getRangeAt(0);
range.deleteContents();
range.insertNode( element );
range.setStartAfter( element );
range.setEndAfter( element );
range.collapse( false );
sel.removeAllRanges();
sel.addRange( range );
}
e_document.updateContent();
if( newLine ) ensureLastLinebreak();
};
var insertElement = function( element, override )
{
if ( override )
{
contentDiv.appendChild( element );
return;
}
_resSelection();
insertAtCaret( element );
};
var replaceToken = function( element )
{
contentDiv.insertBefore( element, this.token );
contentDiv.removeChild( this.token );
};
var parseKeys = function ( match, name, value )
{
this[ name ] = value;
};
var snippetQueue = function( type, alias )
{
var q = snippetTokenQueue[ type ] || [];
if( alias )
{
if( !( alias instanceof Array ) ) alias = [ alias ];
for( var i in alias )
{
q = snippetTokenQueue[ alias[i] ] || [];
if( q.length ) return q;
}
}
return ( snippetTokenQueue[ type ] = q );
};
var parseSnippet = function( match, type, properties, _value, offset )
{
var temp, i, j;
// Texts goes first
if ( lastOffset != offset )
{
// innerText does not work in firefox:(
temp = Dand.wrape( raw.substr( lastOffset, offset - lastOffset ) );
// innerHTML will escape html entities, now replace linebreaks to br
temp.innerHTML = temp.innerHTML.replace( /[\r\n]/g, "<br>" );
IDOMElement( contentDiv ).loot( temp );
}
lastOffset = offset + match.length;
// Snippet Args
temp = { value: _value };
// to ekeys
properties.replace( typeMatch, parseKeys.bind( temp ) );
// Now deal with snippet
/** @type {Astro.Blog.AstroEdit.Visualizer.Snippet.Model} */
var _module = loadedModule[ type ];
if ( _module )
{
// Visualize snippet
new ( _module )( insertElement, snippetWrap, createSnippetMenu, temp );
}
else
{
// no such module, or module is not loaded yet
debug.Info( "[Visualizer] Queueing: " + type );
var token = snippetWrap( "token", type, false );
token.setAttribute( "class", token.getAttribute( "class" ) + " flsf" );
snippetQueue( type ).push([ token, temp ]);
insertElement( token, true );
}
};
var linebreakNodes = ["P", "DIV"];
var linebreakNode = function( name )
{
if( -1 < linebreakNodes.indexOf( name.toUpperCase() ) ) return "\n";
return "";
};
var ensureGoodness = function ()
{
_savSelection();
ensureLastLinebreak();
};
var stepContent = function ( element, level )
{
var j , snippetType
, elements = element.childNodes
, output = "";
for (var i = 0, l = elements.length; i < l; i ++)
{
j = elements[i];
// do nothing on lastline
if (j == lastLine) continue;
if (j.nodeType == 1)
{
snippetType = IDOMElement( j ).getDAttribute( "type" );
if( snippetType && loadedModule[ snippetType = snippetType.toLowerCase() ] )
{
output += loadedModule[ snippetType ].compile( j.firstChild );
}
else if ( j.firstChild )
{
// Text
output += linebreakNode( j.nodeName ) + stepContent(j, ++level);
}
else
{
// Handle special <div><br></div> => one line break
if(l == 1 && j.nodeName.toUpperCase() == "BR") continue;
// Line breaks
output += "\n";
}
}
// Text
else if (j.nodeType == 3)
{
output += j.nodeValue;
}
}
return output;
};
///// Initializations
var snippetReady = function ( e )
{
// Initialize modules
var mod_name = e.substr( e.lastIndexOf(".") + 1, e.length ).toLowerCase()
/** @type {Astro.Blog.AstroEdit.Visualizer.Snippet.Model} */
var _module = __import( e );
var alias = _module.alias;
// Implement module if valid and available
if ( _module && _module.compile )
{
loadedModule[ mod_name ] = _module;
debug.Info( "[Visualizer] Module loaded: " + mod_name );
// Set alias
if ( alias )
{
alias = ( alias instanceof Array ) ? alias : [ alias ];
for ( var k in alias )
{
loadedModule[ alias[k] ] = _module;
debug.Info( "[Visualizer] Alias: " + mod_name + " => " + alias );
}
}
// Append module"s control
temp = Dand.wrapne( "span", mod_name, new IKey( "data-name", mod_name ) );
snippetControls.appendChild( temp );
snippetControls.appendChild( Dand.textNode( "\t" ) );
temp.onclick = new ( _module )( insertElement, snippetWrap, createSnippetMenu );
var queue = snippetQueue( mod_name, _module.alias );
for( var i in queue )
{
var token = queue[i];
new ( _module )( replaceToken.bind({ token: token[0] }), snippetWrap, createSnippetMenu, token[1] );
delete queue[i];
}
}
else
{
if ( _module )
{
delete loadedModule[ mod_name ];
debug.Info( "[Visualizer] Module discarded: invalid module \"" + mod_name + "\"" );
}
else
{
debug.Info( "[Visualizer] Module \"" + mod_name + "\" does not exists" );
}
}
};
this.setContentDiv = function( element )
{
contentDiv = element;
// listeners that return values cannot use addEventListener
contentDiv.onkeypress = function(e)
{
if (e.which == 13)
{
insertAtCaret( Dand.wrap( "br" ) );
_savSelection();
return false;
}
return true;
};
temp = IDOMElement( contentDiv );
temp.addEventListener( "Input", ensureGoodness );
temp.addEventListener( "KeyUp", ensureGoodness );
temp.addEventListener( "Click", ensureGoodness );
contentDiv.focus();
ensureGoodness();
try {
document.execCommand( "insertBrOnReturn", false, "true" );
} catch(e) {
debug.Info( "Not firefox" );
}
};
this.saveRaw = function ()
{
return stepContent( contentDiv, 0 );
};
this.visualizeData = function ( data )
{
if ( !data ) return;
lastOffset = 0;
// clear content
contentDiv.innerHTML = "";
( raw = data ).replace( stackMatch, parseSnippet );
if ( lastOffset != raw.length )
{
// innerText does not work in firefox:(
temp = Dand.wrape( raw.substr( lastOffset, raw.length - lastOffset ) );
// innerHTML will escape html entities, now replace linebreaks to br
temp.innerHTML = temp.innerHTML.replace( /[\r\n]/g, "<br>" );
IDOMElement( contentDiv ).loot( temp );
}
temp = null;
raw = null;
};
this.saveSelection = _savSelection;
this.restoreSelection = _resSelection;
this.insertAtCaret = insertAtCaret;
this.insertSnippet = function( type, options )
{
var _module = loadedModule[ type ];
new ( _module )(
// Disables the override
function( e ) { insertElement( e ); }
, snippetWrap, createSnippetMenu, options
);
};
article.invoke(this);
var modules = [];
for( var i = 0; i < snippetList.length; i ++ )
{
modules[ modules.length ] = snippetNs + snippetList[i];
}
var ldr = new Loader( service_uri, "o" );
ldr.load( modules, snippetReady );
};
ns[ NS_EXPORT ]( EX_CLASS, "Visualizer", Visualizer );
})();

View File

@ -1,256 +0,0 @@
.ae_panel_section {
padding: 0 1em;
color: white;
height: 0;
overflow: hidden;;
}
.ae_section_prop {
margin: 0.5em 0;
text-align: right;
}
.ae_prop_name {
opacity: 0.8;
}
.ae_prop_value {
font-size: 1.2em;
text-align: right;
}
/* Interactive value */
.ae_iValue {
text-align: center;
padding: 0.5em;
cursor: default;
}
.ae_background {
background-color: #fff;
background-image:
linear-gradient(90deg, transparent 1em, #666 1em, #666 1.2em, transparent 1.2em),
linear-gradient(#EEE .1em, transparent .1em);
background-size: 100% 1.5em;
}
/* Buttons */
.ae_purple { background: purple; }
.ae_purple:hover { background: darkmagenta; }
.ae_coral { background: orangered; }
.ae_coral:hover { background: darkorange; }
.ae_dodgerblue { background: dodgerblue; }
.ae_caution { color: red; }
.ae_caution:hover { background: #333; }
.ae_dodgerblue:hover { background: cornflowerblue; }
/* End buttons */
.ae_disabled {
color: grey;
background: none;
}
.ae_blockswitch {
line-height: 2em;
}
.ae_blockswitch > span {
white-space: nowrap;
/* text-transform:uppercase; */
font-family: custom-sans;
padding: 0.2em 0.5em;
cursor: default;
opacity: 0.5;
}
.ae_blockswitch > span:hover {
background-color: black;
opacity: 1;
}
.ae_body {
max-height: 100%;
overflow-y: scroll;
position: fixed;
}
.ae_content {
width: auto;
background: SkyBlue;
}
.ae_panel {
width: 300px;
height: auto;
min-height: 100%;
background: #222;
color: white;
position: absolute;
top: 0;
right: 0;
/* will handel mouse scroll later*/
overflow: hidden;
-moz-box-shadow: -2px 0 5px black;
-webkit-box-shadow: -2px 0 5px black;
box-shadow: -2px 0 5px black;
}
.ae_topbar {
width: 100%;
color: #222;
padding: 0.35em 0;
overflow: hidden;
border-bottom: 7px solid #222;
}
.ae_title, .ae_stitle {
padding: 0.35em;
}
.ae_title {
position: relative;
top: 0.25em;
font-size: 2em;
}
.ae_stitle:hover {
background-color: rgba( 0, 0, 0, 0.2 );
}
.ae_stitle {
font-size: 1.5em;
}
#ae_title {
font-size: 2.5em;
color: #444;
}
#ae_content {
font-size: 100%;
margin-bottom: 100%;
border-bottom: 1px black dashed;
}
#ae_title, #ae_content {
background: none;
width: 100%;
-webkit-box-sizing: border-box;
-moz-box-sizing: border-box;
box-sizing: border-box;
}
#ae_title:focus {
background: rgba(255, 255, 255, 0);
}
#ae_content:focus {
background: rgba(255, 255, 255, 0);
}
#ae_bgdimmer {
background: rgba(255, 255, 255, 0);
}
#ae_content, #ae_bgdimmer {
color: #555;
padding: 1em 1em 0.01em 1em;
}
.ae_preview {
display: block;
color: white;
text-decoration: none;
padding: 0.4em;
font-size: 100%;
width: 100%;
}
.ae_user_info {
background: #111;
overflow: hidden;
position: relative;
}
.ae_draft_section {
padding: 0.5em;
}
.ae_draft_logo {
font-size: 3em;
position: absolute;
opacity: 0.2;
cursor: default;
}
.ae_name {
text-align: right;
padding: 0.2em;
}
.ae_user_content {
padding: 0.2em
}
#ae_user_drafts {
overflow: hidden;
}
.ae_dEntry {
cursor: default;
padding: 0.2em;
background: rgba(255, 255, 255, 0);
}
.ae_dEntry:hover {
background: rgba(255, 255, 255, 0.2);
}
.ae_dEntry_date {
text-align: right;
}
.ae_expand_btn, .ae_callapse_btn {
background: url(/assets/blog/layout-images/collapse.png) center 2.5px no-repeat;
width: 100%;
height: 10px;
}
.ae_expand_btn {
-webkit-transform: rotate(180deg);
-moz-transform: rotate(180deg);
transform: rotate(180deg);
}
.ae_callapse_btn {
-webkit-transform: rotate(0deg);
-moz-transform: rotate(0deg);
transform: rotate(0deg);
}
.ae_affected_count {
color: red;
}
/*Active draft notation*/
.ae_dActive_bubble {
float: right;
color: yellowgreen;
text-shadow: 0 0 5px yellowgreen;
font-size: 80%;
}
body {
margin: 0 auto;
min-width: 1200px;
}

View File

@ -1,143 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.AstroEdit" );
/** @type {System.utils} */
var utils = __import( "System.utils" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
/** @type {Astro.Blog.AstroEdit.Article} */
var Article = __import( "Astro.Blog.AstroEdit.Article" );
/** @type {Astro.Blog.AstroEdit.Draft} */
var Draft = __import( "Astro.Blog.AstroEdit.Draft" );
/** @type {Astro.Blog.AstroEdit.Flag} */
var Flag = __import( "Astro.Blog.AstroEdit.Flag" );
/** @type {Astro.Blog.AstroEdit.Visualizer} */
var Visualizer = __import( "Astro.Blog.AstroEdit.Visualizer" );
/** @type {Astro.Blog.AstroEdit.Uploader} */
var Uploader = __import( "Astro.Blog.AstroEdit.Uploader" );
/** @type {Astro.Blog.AstroEdit.SiteLibrary} */
var SiteLibrary = __import( "Astro.Blog.AstroEdit.SiteLibrary" );
/** @type {Components.Vim.VimArea} */
var VimArea = __import( "Components.Vim.VimArea" );
// calls the smart bar
var SmartInput = __import( "Astro.Blog.AstroEdit.SmartInput" );
// __import( "Astro.Blog.SharedStyle" ); CSS_RESERVATION
var wh, ww, cw, html, article;
var init = function ()
{
//// Component initializations
/** @type {_AstConf_.AstroEdit} */
var a_conf = Config.get( "AstroEdit" );
var base_path = utils.siteProto( Config.get( "BasePath" ) );
Cycle.next(
function()
{
article.load(
a_conf.article_id
, function( obj, id )
{
window.history.replaceState( obj, "", base_path + "astroedit/" + id + "/" );
}
);
}
);
article = new Article(
a_conf.paths.set_article
, [
new Flag( "tags", "ae_tags", a_conf.paths.tags )
, new Flag( "section", "ae_secs", a_conf.paths.sections )
]
);
// Article modules
new Draft( article, a_conf.paths.get_drafts );
var Vis = new Visualizer(
article
, Dand.id( "ae_visual_snippets" )
, Config.get( "ServiceUri" )
);
new SmartInput( Vis );
// Independent modules
new Uploader( a_conf.paths.set_file );
new SiteLibrary(
base_path
, a_conf.paths.get_files
, a_conf.paths.set_file
);
var title = Dand.id("ae_title");
var content = Dand.id("ae_content");
// content height
content.style.minHeight = String(screen.availHeight) + "px";
html = document.body.parentNode;
window.onresize = adjustLayout;
// Setting event handlers
title.onblur = content.onblur = function () { Dand.id("ae_bgdimmer").style.background = ""; };
content.onfocus = content.onfocus = function ()
{
Dand.id("ae_bgdimmer").style.background = "rgba(255, 255, 255, 0.2)";
};
Dand.id( "ae_publish_btn" ).onclick = function () { article.saveAndPublish(); };
Dand.id( "ae_preview_btn" ).onclick = function () { article.preview(); };
Dand.id( "ae_drop_btn" ).onclick = function () { article.drop(); };;
adjustLayout();
VimTrigger();
};
var VimTrigger = function()
{
var f10Binding = function ( e )
{
e = e || window.event;
if ( e.keyCode ) code = e.keyCode;
else if ( e.which ) code = e.which;
if ( code == 121 )
{
e.preventDefault();
var node = document.activeElement;
if( node.nodeName == "TEXTAREA" )
{
new VimArea( node, true );
}
}
};
//Attach the var with the event = function
if(document.addEventListener) document.addEventListener('keydown', f10Binding, false);
else if(document.attachEvent) document.attachEvent('onkeydown', f10Binding);
else document.onkeydown = f10Binding;
};
var adjustLayout = function ()
{
ww = html.clientWidth;
wh = html.clientHeight;
cw = ww - 300;
Dand.id("ae_body").style.width = String(cw) + "px";
};
Bootstrap.regInit( init );
})();

View File

@ -1,14 +0,0 @@
.site-file[data-type="album"] {
column-width: 225px;
column-gap: 0.75em;
}
.site-file[data-type="album"] > div {
display: inline-block;
margin-bottom: 0.5em;
width: 100%;
}
.site-file[data-type="album"] > div img {
width: 100%;
}

View File

@ -1,96 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
/** @type {System.utils.Perf} **/
var Perf = __import( "System.utils.Perf" );
/** @type {Astro.Blog.Config} */
var Conf = __import( "Astro.Blog.Config" );
/** @type {_AstConf_.SiteFile} */
var config = null;
var SiteFile = ns[ NS_INVOKE ]( "SiteFile" );
var BLANK_IMG = __import( "Dandelion.StaticRes.BLANK_IMG" );
var Album = function ( id, hash )
{
if( !config ) throw new Error( "config is not defined" );
var stage = Dand.id( id, true );
var sf = new SiteFile( id, hash );
if( sf.type != "album" ) return;
var ostage = stage.element;
var applyStructure = function( obj )
{
/** @type {_AstJson_.SiteFile} */
var finfo = JSON.parse( obj );
var files = finfo.files;
var l = files.length;
// XXX: Not traditional!
// Maximum of 4 for listing
if( ostage.parentNode.className == "h_img" && 4 < l )
{
l = 4;
}
for( var i = 0; i < l; i ++ )
{
/** @type {_AstJson_.SiteFile} */
var file = files[i];
var uuid = Perf.uuid;
ostage.appendChild( Dand.wrapne(
"div"
, Dand.wrapna( "img", [ new IKey( "src", BLANK_IMG ) ] )
, [ new IKey( "id", uuid ), new DataKey( "size", "medium" ) ]
) );
Cycle.next( function()
{
new SiteFile( this.id, this.info.hash, this.info );
}.bind({ id: uuid, info: file }) );
}
};
var loadFailed = function( obj )
{
console.log( obj );
};
sf.loadInfo( applyStructure, loadFailed );
};
var init = function()
{
config = Conf.get( "SiteFile" );
if( config )
{
var SFOs = Conf.get( "SFObjects" );
for( var i in SFOs )
{
var f = SFOs[i];
new Album( f[0], f[1] );
}
}
};
Bootstrap.regInit( init );
ns[ NS_EXPORT ]( EX_CLASS, "Album", Album );
})();

View File

@ -1 +0,0 @@
.ref-content { display: inline-block; }

View File

@ -1 +0,0 @@
// __namespace( "Astro.Blog.Components.ArticleContent" );

View File

@ -1,35 +0,0 @@
.bubble {
position: fixed;
background: white;
border-radius: 300px;
-moz-box-shadow: 7px 7px 10px;
-webkit-box-shadow: 7px 7px 10px;
box-shadow: 7px 7px 10px;
z-index: 98;
}
.innerBubble {
border-radius: 300px;
position: relative;
overflow: hidden;
}
.innerBubble:before {
content: '';
display: inline-block;
height: 100%;
vertical-align: middle;
}
.bInner{
display: inline-block;
width: 100%;
vertical-align: middle;
text-align: center;
font-size: 1.35em;
color: white;
}

View File

@ -1,133 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {System.utils.EventKey} */
var EventKey = __import( "System.utils.EventKey" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
var Bubble = function () {
this.stage = null;
this.bubble = null;
//// default is somewhat purple
this.bgColor = "#662D91";
this.blowInner = function ()
{
var b_style = this.bubble.style
, s_style = this.stage.style;
b_style.margin = "10px 10px";
b_style.width = "150px";
b_style.height = "150px";
s_style.width = "170px";
s_style.height = "170px";
s_style.bottom = "20px";
s_style.right = "20px";
};
this.blowOuter = function ()
{
var b_style = this.bubble.style
, s_style = this.stage.style;
b_style.margin = "100px 100px";
s_style.width = "200px";
s_style.height = "200px";
s_style.bottom = "10px";
s_style.right = "10px";
Cycle.delay( this.blowInner.bind(this), 250 );
};
this.Void = function ()
{
this.stage.style.display = "none";
};
// Set Bindings
this.init = this.init.bind(this);
this.blurp = this.blurp.bind(this);
this.pop = this.pop.bind(this);
this.setColor = this.setColor.bind(this);
};
var wrapc = function( aClass, elem )
{
return Dand.wrapc( "comp " + aClass, elem );
};
Bubble.prototype.init = function ()
{
this.stage = wrapc( "bubble" );
this.bubble = wrapc( "innerBubble" );
var b_style = this.bubble.style
, s_style = this.stage.style;
b_style.margin = "85px 85px";
b_style.width = "0px";
b_style.height = "0px";
b_style.background = this.bgColor;
b_style.overflow = "hidden";
this.bubble.appendChild(
this.message = wrapc( "bInner flsf" )
);
this.stage.appendChild(this.bubble);
s_style.display = "none";
s_style.width = "10px";
s_style.height = "10px";
s_style.bottom = "85px";
s_style.right = "85px";
// onClick handle to prevent persistent bubble
IDOMElement( this.stage ).addEventListener( new EventKey( "Click", this.blurp ) );
return this.stage;
};
Bubble.prototype.setColor = function (color)
{
this.bubble.style.background = color;
};
Bubble.prototype.blurp = function ()
{
var b_style = this.bubble.style
, s_style = this.stage.style;
b_style.margin = "0 0";
b_style.width = "0px";
b_style.height = "0px";
b_style.overflow = "hidden";
s_style.position = "fixed";
s_style.width = "10px";
s_style.height = "10px";
s_style.bottom = "85px";
s_style.right = "85px";
Cycle.delay( this.Void.bind(this), 250 );
};
Bubble.prototype.pop = function (message)
{
this.message.innerHTML = message;
this.stage.style.display = "block";
Cycle.delay( this.blowOuter.bind(this), 100 );
};
ns[ NS_EXPORT ]( EX_CLASS, "Bubble", Bubble );
})();

View File

@ -1,67 +0,0 @@
.calendar, #timeline {
cursor: default;
}
.calendar{
position: absolute;
display: none;
background: white;
margin: 20px auto;
font-size: 17px;
padding: 3px;
width: 241px;
box-shadow: 3px 3px 4px black;
border: 10px solid dodgerblue;
border-collapse: collapse;
font-family: custom-sans;
}
/*Inline_Blocks*/
.calDate, #calDays > div > span {
display:-moz-inline-block;
display:-moz-inline-box;
display:inline-block;
}
/*End_Inline_Blocks*/
#calDays > div > span {
background: white;
border: 0px solid;
margin: 1.71428%;
padding: 3px 0px 3px 0px;
#:100/7 - (0.24% margin);
width: 10.857%;
text-align: center;
font-size: 0.8em;
}
#calDays>div {
height: 27px;
white-space: nowrap;
}
.calDate {
width: 155px;
text-align: center;
}
.navbtn {
opacity: .5;
width: 17px;
height: 20px;
}
.navbtn:hover {
opacity: 1;
}
.onhover {
border: 3px solid !important;
margin-left: -2px !important;
margin-top: -4px !important;
vertical-align: top;
padding: 0px 1px 2px 0px;
box-shadow: 3px 3px 3px black;
}
.toNorm {
}
#norec{color: #FF7BAC;}
#notfin{color: #3FA9F5;}
#notyet{color: #BDCCD4;}
#today{color: #7AC943;}

View File

@ -1,244 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.utils.Date} */
var XDate = __import( "Astro.utils.Date" );
var Calendar = function ()
{
this.stage = null;
this.calDate = null;
this.show = false;
this.caption = null;
this.calDays = false;
this.currentHandler = function( v ) {
debug.Info( "[Astro.Blog.Components.Calendar] " + v );
};
};
var bodyClick = function ( e )
{
var s = e.target.getAttribute("calObj")
if(s)
{
this.stage.style.display = "none";
this.stage.style.position = "";
this.show = false;
}
if( this.show && !this.istg.contains( e.target ) )
{
this.stage.style.display = "none";
this.stage.style.position = "";
this.show = false;
}
};
var addZero = function ( num )
{
return num < 10
? "0" + String(num)
: String(num)
;
};
Calendar.prototype.init = function()
{
this.stage = Dand.wrapc( "compx calendar" );
this.istg = IDOMElement( this.stage );
this.calDate = new Date;
IDOMElement( document.body ).addEventListener( "Click", bodyClick.bind( this ) );
var tr = Dand.wrap(null, "navbar")
, td = Dand.wrap("span")
, btn = Dand.wrap("a", null, "navbtn")
;
tr.setAttribute("style", "position: relative");
btn.onclick = function (e) { this.nextMon(); }.bind(this);
td.style.textAlign = "right";
td.style.width = "100%";
td.style.position = "absolute";
td.style.left = "0";
btn.appendChild(Dand.textNode("\u25ba"));
td.appendChild(btn);
tr.appendChild(td);
td = Dand.wrap("span");
btn = Dand.wrap("a", null, "navbtn");
btn.appendChild(Dand.textNode("\u25c4"));
btn.onclick = function (e) { this.prevMon(); }.bind(this);
td.style["float"] = "left";
td.style.position = "absolute";
td.appendChild(btn);
tr.appendChild(td);
caption = Dand.wrap("span", null, "calDate");
caption.style.width = "100%";
caption.appendChild(
Dand.textNode(
XDate.MONTH[this.calDate.getMonth()] + ", " + this.calDate.getFullYear()
)
);
tr.appendChild(caption);
this.stage.appendChild(tr);
this.stage.onselectstart = function() { return false;};
return this.stage;
};
Calendar.prototype.pop = function ( dateObj, handler )
{
if( typeof( dateObj ) == "string" )
{
var p = dateObj.split(",");
if ( p.length == 3 )
dateObj = new Date( p[2], p[1] - 1, p[0] );
}
this.draw( dateObj, handler );
this.show = false;
this.stage.style.display = "block";
Cycle.next( function (){ this.show = true; }.bind(this) );
};
Calendar.prototype.draw = function (dateObj, handler)
{
if(!dateObj)
dateObj = new Date;
this.calDate = dateObj;
var mon = dateObj.getMonth()
, yr = dateObj.getFullYear()
, j = dateObj.getDay()
, dt = dateObj.getDate()
, thisDate = new Date
, thisYear = thisDate.getFullYear()
, thisMonth = thisDate.getMonth()
, thisDate = thisDate.getDate()
, thisDate = Number(String(thisYear) + addZero(thisMonth) + addZero(thisDate))
, currHead = String(yr) + addZero(mon)
, currDate;
( typeof handler == "function" ) && ( this.currentHandler = handler );
caption.innerHTML = XDate.MONTH[this.calDate.getMonth()] + ", " + this.calDate.getFullYear();
if(this.calDays)
this.calDays.parentElement.removeChild(this.calDays);
this.calDays = Dand.wrap(null, "calDays");
var days = (mon == 1) ? (yr % 4 == 0 ? 29: 28) : XDate.CAP_MONTHS[mon] ? 30 : 31;
for (var i = 0; i < days; i ++)
{
if(j < 0)
j = 6;
if(dt - i == 1)
break;
j --;
}
var tr = Dand.wrap(), td;
for(i = 0; i < 7; i ++)
{
td = Dand.wrap("span");
td.appendChild( Dand.textNode( XDate.DAY_ABBR[i] ) );
tr.appendChild(td);
}
this.calDays.appendChild(tr);
tr = Dand.wrap();
for(i = 0; i < j; i ++)
{
td = Dand.wrap("span");
td.style.background = "none";
tr.appendChild(td);
}
i = 0;
while( i ++ < days )
{
currDate = Number(currHead + addZero(i));
if(j > 6)
{
j = 0;
this.calDays.appendChild(tr);
tr = Dand.wrap();
}
td = Dand.wrap( "span" );
td.setAttribute( "value", i + "," + (mon + 1) + "," + yr );
td.setAttribute( "onmouseover", "className=\"onhover\";" );
td.setAttribute( "onmouseout", "className=\"toNorm\";" );
// Unique identifier for body click
// to test whether choice is chosen
td.setAttribute("calObj", "1");
td.onclick = function ( e )
{
this.currentHandler( e.target.getAttribute("value") );
}.bind(this);
if(thisDate < currDate)
{
td.setAttribute("id", "notyet");
}
else if(thisDate > currDate)
{
td.setAttribute("id", "norec");
/*
if(!( book[yr] && book[yr][mon + 1] && book[yr][mon + 1][i] )) {
td.setAttribute("id", "norec");
} else if(book[yr][mon + 1][i][1]) {
td.setAttribute("id", "notfin");
}
*/
}
else if(currDate == thisDate)
{
td.setAttribute("id", "today");
currlabel = td;
}
td.appendChild(Dand.textNode(i));
tr.appendChild(td);
j ++;
}
if(j) this.calDays.appendChild(tr);
this.stage.appendChild(this.calDays);
};
Calendar.prototype.prevMon = function () {
this.draw( this.calDate = new Date( this.calDate.getFullYear(), this.calDate.getMonth() - 1 ) );
};
Calendar.prototype.nextMon = function () {
this.draw( this.calDate = new Date( this.calDate.getFullYear(), this.calDate.getMonth() + 1 ) );
};
ns[ NS_EXPORT ]( EX_CLASS, "Calendar", Calendar );
})();

View File

@ -1,288 +0,0 @@
.comment-stage {
width: 80%;
float: right;
padding-bottom: 1em;
position: relative;
}
.c_body {
position: relative;
padding-left: 10px;
}
.c_title {
padding: 1em 0.5em;
}
.c_bsign {
margin-left: -0.47em;
padding: 0.1em 0.5em 0.1em 1em;
font-size: 2em;
color: white;
background: cornflowerblue;
}
.uc_ntoggle {
font-family: custom-sans;
vertical-align: top;
padding: 0.2em 0em;
}
.uc_ntoggle:before { content: '..'; }
.uc_ntoggle:after { content: '!'; }
.cr_ntoggle {
font-family: custom-sans;
padding: 0;
margin: 0;
position: absolute;
width: 1.5em;
height: 1.5em;
bottom: 0;
right: -3em;
border-radius: 2em 2em 2em 0em;
border: 0.5em solid white;
line-height: 1.5em !important;
background-color: white;
/* box-shadow: 2px 2px 10px -5px black; */
}
.cr_ntoggle:before, .cr_ntoggle:after {
padding: 0;
border-radius: 2em;
}
.cr_ntoggle:before {
content: '..';
background-color: slategrey;
}
.cr_ntoggle:after { content: '!'; }
.c_comm {
position: relative;
left: 1.6em;
padding-right: 1.6em;
}
.c_comm > .c_cont:after {
content: "";
width: 0;
height: 0;
border-top: 1em solid transparent;
border-bottom: 1em solid transparent;
border-right: 1em solid white;
position: absolute;
top: 1em;
left: -0.9em;
}
.c_comm > .c_cont:before {
content: "";
top: 0;
left: -2.15em;
position: absolute;
background: cornflowerblue;
width: 8px;
height: 100%;
}
.c_cont {
position: relative;
background-color: white;
padding: 1em;
margin-top: 1em;
border: 1px solid #D7D4C9
}
.c_text {
padding-bottom: 0.5em;
word-wrap: break-word;
}
.c_info > div:first-child, .c_info > div > a {
text-align: right;
color: #D4145A;
}
.c_info > div:last-child {
text-align: right;
color: #AAA;
}
.cu_stack {
/* padding 0.5 - 0.2 border width */
margin: 0 0 -0.3em 0.3em;
position: relative;
text-align: right;
width: 100%;
}
.cu_stack > div {
display: inline-block;
}
.cu_avatar {
/* Equal to the border width */
margin: 0 0 -0.2em 0.5em;
}
.cu_avatar > img {
border: 0.2em white solid;
box-shadow: 0px 0px 5px 0 black;
width: 64px;
height: 64px;
float: right;
}
.reply {
margin-left: 20%;
width: 80%;
}
.reply > .c_cont:after, .r_indicator {
content: "";
width: 0;
height: 0;
border-left: 1em solid transparent;
border-right: 1em solid transparent;
border-bottom: 1em solid white;
position: absolute;
top: 0;
right: 1em;
}
#ri_switch[data-pointy="1"] { top: -1em; }
.c_relative_wrap {
position: relative;
padding: 1em;
background: radial-gradient(circle, rgba(0, 0, 0, 0) 10px, #EEE 10px) 0px 10px, #FFF;
background-size: 20px 20px;
}
.commentblock {
margin-top: 1em;
width: 100%;
position: relative;
#background: white;
}
#c_submit {
background: cornflowerblue;
}
#c_submit:hover {
background: cadetblue;
}
.c_reply {
background: Coral;
}
.c_reply:hover {
background: LightCoral;
}
.c_tag {
cursor: pointer;
position: absolute;
overflow: hidden;
height: 100%;
width: 0;
right: 0;
top: 0;
}
.c_tag > span {
-moz-transform: rotate(90deg);
-moz-transform-origin: 50% 50%;
-webkit-transform: rotate(90deg);
-webkit-transform-origin: 50% 50%;
transform: rotate(90deg);
transform-origin: 50% 50%;
font-size: 1.5em;
display: block;
color: white;
}
.commentInput {
width: 100%;
height: 80px;
font-size: 1.2em;
font-family: custom-sans;
}
.c_caption {
font-size: 1.2em;
font-family: custom-sans;
}
.c_false_input {
font-size: 0.8em;
font-size: custom-serif;
font-style: italic;
color: red;
text-align: right;
height: 0;
overflow: hidden;
}
.nocomment {
font-size: 1.2em;
padding: 1em;
background: white;
font-family: custom-serif !important;
margin: 1em;
}
.info_field > div{
margin: 0.2em 0;
text-align: right;
}
.info_field .website span { width: 20%; }
.info_field .website input { width: 80%; }
iframe[src="about:blank"] {
/* recaptcha about:blank page */
display: none;
}
.commentblock, #capcha_wrapper, #c_input_panel, .c_comm {
-webkit-transition: all 500ms cubic-bezier(0.770, 0.000, 0.175, 1.000);
-moz-transition: all 500ms cubic-bezier(0.770, 0.000, 0.175, 1.000);
-ms-transition: all 500ms cubic-bezier(0.770, 0.000, 0.175, 1.000);
-o-transition: all 500ms cubic-bezier(0.770, 0.000, 0.175, 1.000);
transition: all 500ms cubic-bezier(0.770, 0.000, 0.175, 1.000); /* easeInOutQuart */
-webkit-transition-timing-function: cubic-bezier(0.770, 0.000, 0.175, 1.000);
-moz-transition-timing-function: cubic-bezier(0.770, 0.000, 0.175, 1.000);
-ms-transition-timing-function: cubic-bezier(0.770, 0.000, 0.175, 1.000);
-o-transition-timing-function: cubic-bezier(0.770, 0.000, 0.175, 1.000);
transition-timing-function: cubic-bezier(0.770, 0.000, 0.175, 1.000); /* easeInOutQuart */
}
#c_input_panel.reply {
max-width: 80%;
}
.c_so_sorry {
padding: 0.2em;
font-size: 0.8em;
color: orangered;
display: none;
}

View File

@ -1,625 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components.Comment" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
/** @type {System.Cycle.Trigger} */
var Trigger = __import( "System.Cycle.Trigger" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.EventKey} */
var EventKey = __import( "System.utils.EventKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {System.utils.Perf} */
var Perf = __import( "System.utils.Perf" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
/** @type {Astro.Blog.Config} */
var Conf = __import( "Astro.Blog.Config" );
/** @type {Astro.Blog.Components.Bubble} */
var Bubble = __import( "Astro.Blog.Components.Bubble" );
var postData = __import( "System.Net.postData" );
/** @type {_3rdParty_.Recaptcha} */
var Recaptcha;
var RECAPTCHA_SITE_KEY = null;
/** @type {_AstConf_.UserInfo} */
var currentUser = Conf.get( "UserInfo" );
/** @type {_AstConf_.Comment} */
var Config = Conf.get( "Comment" );
/** @type {_AstConf_.Article} */
var article = Conf.get( "Article" );
/*{{{ Validation Methods */
var v_match = function( str, regEx )
{
// Optional string is empty
if( !str ) return true;
// Not empty, validate
if( str.match( regEx ) != null ) return str;
return false;
};
var validateMail = function ( str )
{
return v_match( str, /^(([^<>()\[\]\.,;:\s@\"]+(\.[^<>()\[\]\.,;:\s@\"]+)*)|(\".+\"))@(([^<>()[\]\.,;:\s@\"]+\.)+[^<>()[\]\.,;:\s@\"]{2,})$/i );
};
var validateURL = function ( str )
{
return v_match( str, /^(https?:\/\/)?([\da-z\.-]+)\.([a-z\.]{2,6})([\/\w \.-]*)*\/?$/ );
};
/* End Validation Methods}}}*/
var wrapc = Dand.wrapc;
var init = function ()
{
// TODO: should add controls to be able to remove comments
var contentHaveText = false
, nameHaveText = false
, fieldReady = false
, releaseReplyLock
, submit_button
, cBubble
, button
, cHeight = 0
, elmH = "1.2em"
, cp = Dand.id( "c_input_panel" )
, contentField = Dand.id( "content_field" )
, nameField = Dand.id( "name_field" )
, c_body = Dand.id( "comment_body" )
// If nameField exists, we assume logged in
, loggedIn = !nameField
, contentHadHaveText = false
, commentInput = function ()
{
// trim whitespaces
contentHaveText = contentField.value.trim();
if( contentHaveText != contentHadHaveText ) {
fieldReadyTrigger();
contentHadHaveText = contentHaveText;
}
}
, nameHadHaveText = false
, nameInput = function ()
{
if( !nameField )
return;
// trim whitespaces
nameHaveText = nameField.value.trim();
if( nameHadHaveText != nameHaveText ) {
fieldReadyTrigger();
nameHadHaveText = nameHaveText;
}
}
, doReply = function ()
{
var c_reply = this;
// This will ensure capcha_wrapper is set
fieldReadyTrigger();
// Set comment id
submit_button.setAttribute( new DataKey( "cid", c_reply.getAttribute( "value" ) ) );
// close the triangle in the top rigth corner
Dand.id( "ri_switch", true ).removeAttribute( "data-pointy" );
// If this button is not that button
button && ( c_reply != button ) && releaseReplyButton();
// Lock reply button
c_reply.setAttribute("locked", "1");
c_reply.onclick = null;
c_reply.style.cursor = "default";
c_reply.style.background = "Crimson";
c_reply.style.width = "1.2em";
c_reply.style.right = "-1.2em";
// Configure release lock
button = c_reply;
hideSubmit();
Cycle.delay( function() {
closeInputPanel( function() {
cp.classList.add( "reply" );
reviveInputpanel.bind( c_reply.parentNode.parentNode )();
} );
}, 500);
}
, releaseReplyButton = function ()
{
button.removeAttribute("locked");
button.onclick = doReply.bind(button);
button.style.cursor
= button.style.background
= button.style.width
= button.style.right
= "";
}
, fieldReadyTrigger = loggedIn
? /* Overload */ function ()
{
submit_button || ( submit_button = Dand.id( "c_submit", true ) );
if(contentHaveText)
{
// show submit button
showSubmit();
fieldReady = true;
}
else
{
// hide submit button
hideSubmit();
fieldReady = false;
}
}
: /* Overload */ function ()
{
submit_button || ( submit_button = Dand.id( "c_submit", true ) );
if(!fieldReady && contentHaveText && nameHaveText)
{
// show submit button
showSubmit();
fieldReady = true;
}
else if(!(contentHaveText || nameHaveText))
{
// hide submit button
hideSubmit();
fieldReady = false;
}
}
, submitComment = loggedIn
? /* Overload */ function ()
{
// Postdata
var p = {
"article_id": article.id
, "name": currentUser.name
, "website": currentUser.website
, "avatar": currentUser.avatar
}
// pass-through obj
, comment_id = submit_button.getDAttribute( "cid" );
p.article_id = article.id;
// Set comment id if available
comment_id && ( p["comment_id"] = comment_id );
hideSubmit();
if( getFieldsValidated(p) )
{
popBubble();
// Post the data, bind obj to Handler
postData( Config.processor, p, commentSuccess.bind(p), commentFailed );
}
else
{
Cycle.delay( showSubmit, 1500 );
}
}
: /* Overload */ function ()
{
var p = { "article_id": article.id }
, comment_id = submit_button.getDAttribute( "cid" );
// Set comment id if available
comment_id && ( p["comment_id"] = comment_id );
hideSubmit();
if( getFieldsValidated( p ) )
{
popBubble();
Recaptcha.execute( RECAPTCHA_SITE_KEY, { "action": "submit" } )
.then(function( token )
{
p[ "token" ] = token;
// Post the data, bind obj to Handler
postData( Config.processor, p, commentSuccess.bind(p), commentFailed );
});
}
else
{
Cycle.delay( showSubmit, 1500 );
}
}
, commentSuccess = function ( obj )
{
// Pass Color = Green
cBubble.setColor("YellowGreen");
// Popup Success message
cBubble.pop("Success");
// blurp after 1 sec
Cycle.delay( function (){ cBubble.blurp(); }, 1500 );
generateCommentStack( this, obj );
}
// Input panel control
, closeInputPanel = function (handler) {
cHeight = cp.clientHeight;
cp.style.transition = "all 0s";
cp.style.height = cHeight + "px";
cp.style.overflow = "hidden";
// Delay for 10 millisec for establishing transition properties
Cycle.next(function() {
this.style.transition = "";
}.bind(cp));
Trigger.transition(cp.style, "", function()
{
cp.style.padding = "0";
cp.style.height = "0";
});
// After transition finished, remove input panel
Cycle.delay(function()
{
cp.parentNode.removeChild(cp);
// Pass panel to handler
if(handler) handler();
}, 500);
}
, openInputPanel = function ()
{
cp.style.padding = "";
cp.style.height = cHeight + "px";
// Delay for 500 millisec waiting for transition finished
Cycle.delay(function()
{
cp.style.transition = "all 0s";
cp.style.height = "";
cp.style.overflow = "";
// Pop back up the pointy triangle
Dand.id( "ri_switch", true ).setAttribute( new DataKey( "pointy", "1" ) );
fieldReady = false;
fieldReadyTrigger();
}, 500);
}
, reviveInputpanel = function ()
{
this.appendChild(cp);
Cycle.next(openInputPanel);
}
// Comments submission and handling
, commentFailed = function (obj)
{
// Handle error here to prevent accidental catch by caller
try
{
if(obj != null)
{
if(obj.reload)
{
Cycle.delay(showSubmit, 1500);
Cycle.delay( function()
{
this.innerHTML = "Recaptcha failure";
this.style.height = "1.2em";
}.bind(f), 500 );
Cycle.delay(function (){cBubble.blurp();}, 500);
}
else
{
// Reload not needed, serious error had occurred
Cycle.delay(function (){cBubble.blurp();}, 500);
Cycle.delay(function ()
{
cBubble.setColor("red");
cBubble.pop("Server error");
}, 1000);
}
}
else
{
Cycle.delay(showSubmit, 1500);
Cycle.delay(function (){cBubble.blurp();}, 500);
Cycle.delay(function ()
{
cBubble.setColor("red");
cBubble.pop("Cannot connect");
}, 1000);
}
}
catch(e)
{
debug.Error(e);
}
}
, submitKey = new EventKey("Click", submitComment)
, showSubmit = function ()
{
// prevent multiple prop assign
if( !submit_button.hasListener( submitKey ) )
{
submit_button.style.width = "1.2em";
submit_button.style.right = "-1.2em";
submit_button.style.cursor = "pointer";
}
submit_button.addEventListener( submitKey );
}
, hideSubmit = function ()
{
// prevent multiple prop assign
if( submit_button.hasListener( submitKey ) )
{
submit_button.style.cursor = "default";
submit_button.style.width = "";
submit_button.style.right = "";
}
submit_button.removeEventListener( submitKey );
}
, __createContentText = function( text )
{
var e = wrapc( "c_text", text );
e.innerHTML = e.innerHTML.replace( /\n/g, "<br />" );
return e;
}
, generateCommentStack = function ( rObj, obj )
{
var
// Hold for transitions
c_ind, c_cont, cpole
// The info stack
, _c_info = wrapc("c_info",
[
wrapc("fls", rObj.website ? Dand.wrapne( "a", rObj.name, IKey.quickDef( "target", "_blank", "href", rObj.website ) ) : rObj.name )
, wrapc( "flsf", obj.time )
])
// loggedIn Overload
, c_info = loggedIn
? wrapc("cu_stack", [ _c_info
, Dand.textNode(" ")
, wrapc("cu_avatar"
, Dand.wrapna( "img", IKey.quickDef( "src", rObj.avatar, "alt", "avatar" ) )
)]
)
: _c_info
// Generate comment stack
, c_stack = rObj["comment_id"]
// Reply Structure
? wrapc("reply", wrapc("c_cont", [ c_ind = wrapc("r_indicator") , __createContentText( rObj.content ) , c_info ]))
: wrapc("c_comm",
[
c_ind = wrapc("c_indicator")
, c_cont = wrapc("c_cont", [ cpole = wrapc("cpole") , __createContentText( rObj.content ) , c_info ])
]
)
;
// Remove transition properties
c_stack.style.transition = "all 0s";
// Close Input panel
closeInputPanel( null );
// Remove false_fields
for(var i in fields) {
i = Dand.id("false_" + fields[i]);
i.parentNode.removeChild(i);
}
c_stack.style.opacity = 0;
cp.parentNode.insertBefore( c_stack, cp );
c_stack.style.marginTop = ( -c_stack.clientHeight ) + "px";
// if nocomment notice exist, remove it
if( i = Dand.id("nocomment") )
{
i.style.transition = "all 0s";
i.style.width = "658px";
i.style.height = "22px";
i.style.overflow = "hidden";
// transition
Cycle.next(function()
{
this.style.transition = "";
this.style.margin = "0";
this.style.width = "0";
this.style.padding = "0";
this.style.height = "0";
}.bind(i));
// Pending remove
Trigger.height(i, 0, function(){ this.parentNode.removeChild(this); }.bind(i));
}
// Delay for 10 millisec for establishing transition properties
Cycle.next( function() { this.style.transition = ""; }.bind( c_stack ) );
Cycle.delay(function()
{
this.style.marginTop = "";
this.style.opacity = 1;
}.bind(c_stack), 600);
}
// Validation
, fields = loggedIn ? ["content"] : [ "content", "name", "email", "website", "email_notify" ]
, getFieldsValidated = function (obj)
{
var name, field, falsefield, f;
for(var i in fields)
{
name = fields[i];
field = name + "_field";
falsefield = "false_" + name;
f = Dand.id( falsefield );
if( f ) f.style.height = 0;
switch(name)
{
case "name":
if(!( obj[name] = Dand.id(field).value.trim() ))
Cycle.delay( function() { this.style.height = elmH; }.bind(f), 500 );
break;
case "content":
if(!( obj[name] = Dand.id(field).value.trim() ))
Cycle.delay( function() { this.style.height = elmH; }.bind(f), 500 );
break;
case "website":
if(!( obj[name] = validateURL( Dand.id(field).value.trim() )))
{
obj[name] = false;
Cycle.delay( function() { this.style.height = elmH; }.bind(f), 500 );
}
else
{
if(obj[name] == true)
delete obj[ name ];
}
break;
case "email":
if(!( obj[name] = validateMail( Dand.id(field).value.trim() ) ))
{
obj[name] = false;
Cycle.delay( function() { this.style.height = elmH; }.bind(f), 500 );
}
else
{
if( obj[ name ] == true )
delete obj[ name ];
}
break;
case "email_notify":
if( obj[ name ] = Dand.id( field ).checked )
{
if( obj[ "email" ] == undefined )
{
obj[ name ] = false;
Cycle.delay( function() { this.style.height = elmH; }.bind(f), 500 );
}
}
else
{
delete obj[ name ];
}
break;
}
}
for( var i in obj )
if( !obj[i] ) return false;
return true;
}
, showReplyButton = function ()
{
this.style.width = "1.2em";
this.style.right = "-1.2em";
}
, hideReplyButton = function ()
{
if(!this.getAttribute("locked"))
this.style.width = this.style.right = "";
}
, popBubble = function ()
{
if(cBubble == null)
{
// create a new bubble
cBubble = new Bubble();
document.body.appendChild( cBubble.init() );
// pop message
cBubble.setColor( "cornflowerblue" );
Cycle.next( function () { cBubble.pop("Submitting"); } );
}
}
;
if( !loggedIn )
{
IDOMElement( nameField ).addEventListener( "Input", nameInput );
}
IDOMElement( contentField ).addEventListener( "Input", commentInput );
var l = c_body.childNodes, c_id;
for( var i in l )
{
if( l[i].nodeType == 1
&& ( c_id = IDOMElement( l[i] ).getDAttribute("value") )
)
{
var reply_button = Dand.id("c_reply_" + c_id);
reply_button.onclick = doReply.bind(reply_button);
l[i].onmouseover = showReplyButton.bind(reply_button);
l[i].onmouseout = hideReplyButton.bind(reply_button);
}
}
if( !loggedIn )
{
var limit = 5;
var i = 0;
var reUUID = Perf.uuid;
RECAPTCHA_SITE_KEY = Dand.id( "recaptcha-js" ).src.split( "?render=" )[1];
Cycle.perma(
reUUID, function()
{
if( limit < i ++ )
{
var mesg = Dand.glass( "c_so_sorry" );
if( mesg.length ) mesg[0].style.display = "block";
}
if(( Recaptcha = window["grecaptcha"] ))
{
Cycle.permaRemove( reUUID );
debug.Info( "Recaptcha instance is up" );
}
} , 500
);
}
Cycle.next( nameInput );
Cycle.next( commentInput );
};
Bootstrap.regInit( init );
})();

View File

@ -1,50 +0,0 @@
.control_panel {
height: 100%;
margin-top: 0.2em;
}
.control_panel > a {
display: inline-block;
position: relative;
overflow: hidden;
width: 80px;
height: 80px;
}
.control_panel > a:after {
content: attr(data-desc);
font-family: custom-sans;
background-color: rgba(0, 0, 0, 0.6);
color: white;
position: absolute;
width: 100%;
padding: 0 0.2em;
left: 0;
bottom: 0;
-moz-box-sizing: border-box;
-webkit-box-sizing: border-box;
box-sizing: border-box;
}
.control_panel > a > span {
padding: 0.2em 0.5em;
background-color: orange;
color: white;
}
.control_panel > div {
font-size: 0.8em;
font-family: custom-sans;
}
.control_panel > div > a {
color: #222;
}

View File

@ -1 +0,0 @@
// __namespace( "Astro.Blog.Components.ControlPanel" );

View File

@ -1,6 +0,0 @@
.tags > a {
color: saddlebrown;
font-family: custom-sans;
padding: 0.2em;
float: left;
}

View File

@ -1 +0,0 @@
// __namespace( "Astro.Blog.Components.CrowdTag" );

View File

@ -1,123 +0,0 @@
.b_entry img {
max-width: 100%;
height: auto;
}
.inline-code {
font-family: site-mono;
font-size: 1.12em;
color: black;
background-color: #EEE;
padding: 0.2em 0.5em;
}
.b_entry {
background-color: #FAFAFA;
/* box-shadow: 0 0 8px -2px black; */
border: 1px solid #D7D4C9;
word-wrap: break-word;
position: relative;
margin-top: 0;
padding: 1em;
}
.b_entry.archived::after {
display: block;
content: "Archived";
text-align: center;
background:
linear-gradient(-45deg, transparent 36%, black 36%, black 82%, transparent 82%)
, linear-gradient(45deg, transparent 36%, black 36%, black 82%, transparent 82%);
color: white;
position: absolute;
width: 4.4em;
right: -2.25em;
top: 1.45em;
font-size: 1.5em;
padding: 0.15em 2.25em;
transform: rotate(45deg);
opacity: 0.5;
}
.b_title {
font-family: custom-serif;
font-size: 2.5em;
margin-bottom: 0.25em;
color: #444;
}
.b_avartar {
margin: 0 0 0.5em 0.5em;
line-height: 0;
float: right;
-moz-box-shadow: 2px 2px 5px 0 black;
-webkit-box-shadow: 2px 2px 5px 0 black;
box-shadow: 2px 2px 5px 0 black;
border: 0.4em solid white;
background-color: white;
background-position: center;
background-repeat: no-repeat;
}
.b_bodyWrapper {
color: #555;
text-align: justify;
min-height: 155px;
margin-bottom: 3em;
}
.b_bodyWrapper a { color: #f15a24; }
.b_edit {
background-color: yellowgreen;
}
.b_preview {
background-color: orangered;
}
.b_author {
color: purple;
text-align: right;
}
.b_entry .top-date {
float: right;
opacity: 0.35;
}
.b_entry .top-date:hover {
opacity: 0.6;
}
.b_date, .b_mdate {
text-align: right;
}
.b_date {
font-family: custom-serif;
}
.b_mdate {
font-style: italic;
font-family: custom-sans;
font-size: 0.8em;
opacity: 0.5;
}
.b_tags > a {
font-size: 1em;
color: #76400C;
}

View File

@ -1,28 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components.Entry.Blog" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
/** @type {Astro.utils.Date} */
var XDate = __import( "Astro.utils.Date" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
var init = function()
{
var entry = Dand.id( "b_entry", true );
var time = new Date( entry.getDAttribute( "time" ) );
entry.element.insertBefore(
Dand.wrapc(
"top-date"
, Dand.textNode( XDate.chinese( time ) )
)
, entry.first( 1 )
);
};
Bootstrap.regInit( init );
})();

View File

@ -1,124 +0,0 @@
.home_entry {
position: relative;
margin: 1em 0;
}
.h_info {
position: absolute;
height: 100%;
width: 7em;
text-align: right;
}
.h_body {
margin-left: 7em;
margin-right: 0.5em;
}
.h_bodyWrapper {
border: 1px solid #D4D7C9;
background-color: #FAFAFA;
color: #777;
padding: 1em 1em 2em 1em;
min-height: 155px;
/* Same as image size */
max-width: 600px;
}
.h_datetime {
right: 0;
bottom: 0.95em;
}
.h_auth_com {
padding-top: 0.5em;
font-family: Calibri;
color: #D4145A;
}
.h_avatarWrapper {
display: block;
width: 80px;
height: 80px;
}
.h_avatar, .a_avatarWrapper {
width: 80px;
height: 80px;
margin: 0 auto;
}
.h_avatar {
border-radius: 80px;
background-color: #FAFAFA;
background-size: 50px 50px;
background-repeat: no-repeat;
background-position: center;
-moz-box-shadow: 2px 2px 5px 0 black;
-webkit-box-shadow: 2px 2px 5px 0 black;
box-shadow: 2px 2px 5px 0 black;
}
.h_avatar:hover {
width: 70px;
height: 70px;
border-radius: 70px;
margin-top: 5px;
background-size: 60px 60px;
}
.h_infoWrapper {
padding: 0.5em;
}
.h_cCount {
font-family: sans-serif;
color: cornflowerblue;
font-size: 80%;
}
.h_title {
font-size: 2em;
color: #444;
}
.h_title, .h_desc {
overflow: hidden;
text-overflow: ellipsis;
}
.h_read_full {
position: absolute;
bottom: 0.5em;
right: 1.5em;
font-size: 0.8em;
text-align: right;
padding: 0.5em 0 0.5em 0;
color: #F15A24;
}
.h_read_full_a {
color: #F15A24;
}
.h_img {
width: 100%;
max-height: 350px;
overflow: hidden;
}
.h_img img {
max-width: 100%;
height: auto;
}

View File

@ -1 +0,0 @@
// __namespace( "Astro.Blog.Components.Entry.Home" );

View File

@ -1,67 +0,0 @@
.list_entry {
position: relative;
margin: 1em 0;
padding: 0.5em;
background-color: #FAFAFA;
border: 1px solid #D4D7C9;
}
.caption {
font-size: 2.5em;
color: #444;
}
.title {
font-size: 1.5em;
color: #555;
}
.content {
color: #777;
}
.tags {
padding: 0.5em 0;
}
.flag {
font-family: custom-sans;
font-size: 0.8em;
padding: 0 0.5em;
margin: 0 0 0 0.2em;
float: right;
cursor: default;
}
.flag.archived { color: white; background: #888; }
.flag.archived:hover { background: #666; }
.flag.featured { color: white; background: coral; }
.flag.featured:hover { background: orangered; }
.tag {
color: #76400C;
padding: 0.2em 0.5em;
font-family: custom-sans;
}
.mdate, .author {
text-align: right;
}
.author {
color: crimson;
}
.mdate {
color: #AAA;
font-size: 0.8em;
font-family: custom-sans;
}

View File

@ -1 +0,0 @@
// __namespace( "Astro.Blog.Components.Entry.List" );

View File

@ -1,68 +0,0 @@
.t_title {
font-size: 2.5em;
color: #444;
}
.ts_title {
font-size: 1.5em;
color: #555;
}
ul.n-archive > li {
position: relative;
padding: 0.5em 0.5em 0.1em;
margin: 0.5em;
border-right: 1px solid transparent;
}
ul.n-archive > li:hover {
border-right: 1px solid #555;
}
ul.n-archive h4 {
color: black;
}
ul.n-archive a {
color: #666;
width: 100%;
display: inline-block;
}
ul.n-archive a:before {
content: attr(data-value);
margin-right: 0.5em;
padding: 0.5em;
float: left;
width: 1.4em;
text-align: center;
color: white;
font-family: custom-sans;
}
ul.n-archive a:hover:before {
text-decoration: underline;
}
ul.n-archive a:hover {
text-decoration: none;
}
ul.n-archive a.Sun:before { color: rgba(255, 29, 37, 1); }
ul.n-archive a.Mon:before { color: rgba(102, 45, 145, 1); }
ul.n-archive a.Tue:before { color: rgba(63, 169, 245, 1); }
ul.n-archive a.Wed:before { color: rgba(122, 201, 67, 1); }
ul.n-archive a.Thu:before { color: rgba(255, 123, 172, 1); }
ul.n-archive a.Fri:before { color: rgba(96, 56, 19, 1); }
ul.n-archive a.Sat:before { color: rgba(255, 147, 30, 1); }
ul.n-archive a.Sun:hover:before { color: white; background: rgba(255, 29, 37, 1); }
ul.n-archive a.Mon:hover:before { color: white; background: rgba(102, 45, 145, 1); }
ul.n-archive a.Tue:hover:before { color: white; background: rgba(63, 169, 245, 1); }
ul.n-archive a.Wed:hover:before { color: white; background: rgba(122, 201, 67, 1); }
ul.n-archive a.Thu:hover:before { color: white; background: rgba(255, 123, 172, 1); }
ul.n-archive a.Fri:hover:before { color: white; background: rgba(96, 56, 19, 1); }
ul.n-archive a.Sat:hover:before { color: white; background: rgba(255, 147, 30, 1); }

View File

@ -1 +0,0 @@
// __namespace( "Astro.Blog.Components.Entry.Tag" );

View File

@ -1,90 +0,0 @@
.tile-block {
float: left;
width: 150px;
height: 150px;
position: relative;
overflow: hidden;
display: inline-block;
background-image: linear-gradient(
135deg, transparent 40%, rgba(0,0,0,.2) 40%, rgba(0,0,0,.2) 60%, transparent 60%
)
, linear-gradient(
225deg, transparent 40%, rgba(0,0,0,.2) 40%, rgba(0,0,0,.2) 60%, transparent 60%
)
, linear-gradient( 45deg, rgba(0,0,0,.2) 0%, rgba(0,0,0,.2) 10%, transparent 10% )
, linear-gradient( 135deg, rgba(0,0,0,.2) 0%, rgba(0,0,0,.2) 10%, transparent 10% )
, linear-gradient( 225deg, rgba(0,0,0,.2) 0%, rgba(0,0,0,.2) 10%, transparent 10% )
, linear-gradient( 315deg, rgba(0,0,0,.2) 0%, rgba(0,0,0,.2) 10%, transparent 10% )
;
background-size: 100px 100px;
background-color: white;
border: 1px solid #d4d7c9;
}
.tile-block .banner {
background-repeat: no-repeat;
background-position: center center;
opacity: 0.9;
background-color:white;
}
.tile-block .banner, .tile-block .link {
width: 100%;
height: 100%;
position: absolute;
top: 0;
left: 0;
}
.tile-block .link {
background-color: black;
color: white;
opacity: 0;
text-align: center;
text-decoration: none;
padding-top: 55%;
background-image: linear-gradient(
135deg, transparent 40%, rgba(255,255,255,.1) 40%, rgba(255,255,255,.1) 60%, transparent 60%
)
, linear-gradient(
225deg, transparent 40%, rgba(255,255,255,.1) 40%, rgba(255,255,255,.1) 60%, transparent 60%
)
, linear-gradient( 45deg, rgba(255,255,255,.1) 0%, rgba(255,255,255,.1) 10%, transparent 10% )
, linear-gradient( 135deg, rgba(255,255,255,.1) 0%, rgba(255,255,255,.1) 10%, transparent 10% )
, linear-gradient( 225deg, rgba(255,255,255,.1) 0%, rgba(255,255,255,.1) 10%, transparent 10% )
, linear-gradient( 315deg, rgba(255,255,255,.1) 0%, rgba(255,255,255,.1) 10%, transparent 10% )
;
background-size: 100px 100px;
background-position: 100% 0;
-webkit-transition: all 200ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-moz-transition: all 200ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-ms-transition: all 200ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-o-transition: all 200ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
transition: all 200ms cubic-bezier(0.215, 0.610, 0.355, 1.000); /* easeOutCubic */
-webkit-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
-moz-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
-ms-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
-o-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000); /* easeOutCubic */
}
.tile-block .link:hover {
padding-top: 50%;
opacity: 1;
}
.tile-block .title {
margin-top: -0.5em;
}

View File

@ -1 +0,0 @@
// __namespace( "Astro.Blog.Components.Entry.Tile" );

View File

@ -1,35 +0,0 @@
.footnote {
padding-top: 0.25em;
position: relative;
margin-bottom: 2em;
}
.footnote a {
color: #f15a24;
}
.footnote {
color: #555;
list-style-type: decimal;
list-style-position: inside;
}
.footnote > li {
padding-left: 0.5em;
}
.footnote > li[focused] {
background-color: #EE5;
}
.footnote:before {
content: "";
position: absolute;
top: 0;
width: 40%;
border-top: 1px black solid;
}

View File

@ -1,46 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components.Footnote" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
/** @type {Astro.utils.Date} */
var XDate = __import( "Astro.utils.Date" );
/** @param {Dandelion.IDOMElement} elem */
var Footnote = function( elem )
{
var jumpers = Dand.glass( "ft", true );
if( !jumpers.length ) return;
var notes = Dand.glass( "footnote", true )[0];
jumpers.forEach( function( e ) {
var a = e.first( 1 );
IDOMElement( a ).addEventListener( "Click", function()
{
var clicked = a.hash.substr( 1 );
notes.foreach( 1, function( e ) {
if( e.id == clicked )
{
e.setAttribute( "focused", 1 );
}
else
{
e.removeAttribute( "focused" );
}
});
});
} );
};
Bootstrap.regInit(function() {
new Footnote();
});
})();

View File

@ -1,172 +0,0 @@
.notifications {
float: right;
cursor: default;
position: relative;
}
.nt_body {
position: absolute;
top: 0;
left: -300px;
max-width: 300px;
text-align: left;
display: none;
z-index: 1;
}
.nt_body > div { float: right; }
.nt_button {
float: left;
text-align: left;
display: block;
padding: 0 0.5em 0 0;
color: white;
background-color: #444;
}
.nt_button:before {
content: attr(data-count);
display: inline-block;
padding: 0 0.5em;
margin-right: 0.5em;
line-height: 2em;
background-color: royalblue;
}
.nt_button:before, .nt_switch:before, .nt_icon_settings {
-webkit-transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-moz-transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-ms-transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-o-transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000); /* easeOutCubic */
-webkit-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
-moz-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
-ms-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
-o-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000); /* easeOutCubic */
}
.nt_button:hover:before {
background: dodgerblue;
}
.nt_arrow {
margin-top: 0.2em;
border-top: 0.8em solid transparent;
border-left: 1em solid #444;
border-bottom: 0.8em solid transparent;
}
.nt_container {
min-width: 300px;
padding: 0.5em;
background: #444;
margin-right: 0.5em;
margin-top: -2em;
overflow: hidden;
}
.nt_date {
text-align: right;
}
.nt_container > ul {
max-height: 400px;
width: 120%;
white-space: nowrap;
text-overflow: ellipsis;
overflow-y: scroll;
color: white;
}
.nt_container > ul > li {
width: 80%;
padding: 0.25em 0.5em;
color: white;
text-decoration: none;
}
.nt_container > ul > li:hover {
background-color: orangered;
}
.nt_icon_settings {
float: right;
padding: 0em 0.2em;
width: 2em; height: 2em;
background: #333 url(/assets/blog/layout-images/settings.png) no-repeat center center;
background-size: 1.5em 1.5em;
}
.nt_icon_settings:hover {
background-color: #555;
}
ul.nt_smenu {
font-family: custom-sans;
cursor: default;
}
ul.nt_smenu > li {
padding: 0.2em 0.5em;
}
ul.nt_smenu > li:hover {
background-color: black;
}
ul.nt_smenu > li[active] > span.nt_switch:before {
margin-top: -1.2em;
}
ul.nt_smenu > li > span {
display: inline-block;
vertical-align: top;
}
.nt_switch {
width: 2.5em;
height: 1.2em;
text-align: center;
overflow: hidden;
}
.nt_switch:before {
float: left;
color: red;
content: 'OFF';
}
.nt_switch:after {
float: left;
color: yellowgreen;
content: 'ON';
}
.nt_tname {
padding-left: 0.5em;
}
.nt_tcount {
float: right;
}

View File

@ -1,240 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components.Notification" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
/** @type {System.Cycle} */
var Cycle = __import( "System.Cycle" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
/** @type {System.utils.EventKey} */
var EventKey = __import( "System.utils.EventKey" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
/** @type {Components.Mouse.ContextMenu} */
var ContextMenu = __import( "Components.Mouse.ContextMenu" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
/** @type {Astro.utils.Date} */
var XDate = __import( "Astro.utils.Date" );
var postData = __import( "System.Net.postData" );
var smstamp = __import( "Astro.utils.Date.smstamp" );
var init = function ()
{
var stage = Dand.id( "notifications" );
var bodyStyle = Dand.id( "nt_body" ).style;
/** @type {_AstConf_.Notification} */
var conf = Config.get( "Notification" );
var processor = conf.processor;
var contextMenu;
var itemsMenu;
var nError = function( e ) {
// TODO: Do something on error
debug.Info( e );
};
var followLink = function(e)
{
window.location = this.link;
};
var toggleFollow = function(e)
{
var _action = "enable";
if( this.item.getAttribute( "active" ) )
{
_action = "disable";
if(
0 < IDOMElement( this.count ).getDAttribute( "count" )
&& !confirm( "All followed notifications of this type will be unfollowed. Continue?" )
) return;
}
postData(
processor
, {
"action": _action
, "tid": IDOMElement( this.item ).getDAttribute( "tid" )
, "cid": 0
}
, toggleSuccess.bind(this)
, nError
);
};
var toggleSuccess = function(e)
{
if( this.item.getAttribute( "active" ) )
{
this.item.removeAttribute( "active" );
this.count.innerHTML = "N/A";
}
else
{
this.item.setAttribute( "active", 1 );
this.count.innerHTML = "0";
}
};
var showSettings = function( e )
{
// Create list <ul> <li> ... </ul>
var ul = Dand.wrap("ul", "nt_imenu", "nt_smenu");
for( var i in e.data )
{
var data = e.data[i];
var li
, li_s = [
// On/off toggle
Dand.wrap( "span", null, "nt_switch" )
, Dand.wrap( "span", null, "nt_tname", data.name )
]
, keys = [ new DataKey( "tid", data.type ) ]
;
if( data.hasOwnProperty("count") )
{
// type count
li_s[2] = Dand.wrap(
"span"
, null
, "nt_tcount"
, e.data[i].count + ""
, new DataKey( "count", data.count )
);
// Active
keys[ keys.length ] = new IKey( "active", 1 );
}
else
{
li_s[2] = Dand.wrap( "span", null, "nt_tcount", "N/A" );
}
// Create li element
li = Dand.wrapne( "li", li_s, keys );
ul.appendChild( li );
IDOMElement( li ).addEventListener(
"Click"
, toggleFollow.bind({ item: li, count: li_s[2] })
);
}
var msgBox = new MessageBox( "Notification Settings", ul, "Close" ).show();
};
var popupSettings = function()
{
postData( processor, { action: "getSettings" }, showSettings, nError );
};
var readNotification = function(e)
{
postData( processor, { action: "read", id: this.id }, followLink.bind( this ), nError );
};
// functions
var createContextMenu = function(e)
{
var items = [], menuShow = false;
var hasNotis = 0 < e.data.length;
for( var n in e.data )
{
/** @type {_AstJson_.AJaxGetNotis} */
var data = e.data[n];
// Create items
items[ items.length ] = new IKey(
data.mesg
, new EventKey(
"m_" + data.id
, readNotification.bind( data )
)
);
}
Dand.glass( "nt_icon_settings", true )[0].addEventListener( "Click", popupSettings );
contextMenu = new ContextMenu(
Dand.id( "nt_open_menu" )
, items
, "LMB"
, nt_body
// showMenu/hideMenu overrides style settings
, {
"class": "nt_container"
, "showMenu": function( stage, event )
{
if( stage.className == "nt_date" ) return;
if( !hasNotis || menuShow ) return;
bodyStyle.marginLeft = "1em";
bodyStyle.marginRight = "-1em";
bodyStyle.opacity = 0;
bodyStyle.display = "block";
Cycle.next(function()
{
bodyStyle.marginLeft
= bodyStyle.marginRight = 0;
bodyStyle.opacity = 1;
menuShow = true;
});
}
, "hideMenu": function( stage )
{
if( stage.className == "nt_date" ) return;
if( !menuShow ) return;
bodyStyle.marginLeft = "1em";
bodyStyle.marginRight = "-1em";
bodyStyle.opacity = 0;
Cycle.delay(function()
{
bodyStyle.display = "none";
// cubic 200, we set delay to 200
menuShow = false;
}, 200);
}
// Prevent default subnode chaining
, "chainHide": function( stage ) { }
, "chainShow": function( stage ) { }
}
);
for( n in e.data )
{
/** @type {_AstJson_.AJaxGetNotis} */
var data = e.data[n];
var li = contextMenu.getItemByKey( "m_" + data.id ).stage;
li.appendChild(
Dand.wrapc(
"nt_date"
, smstamp( new Date( data.date ) )
)
);
}
};
postData( processor, { "action": "get" }, createContextMenu );
};
Bootstrap.regInit( init );
})();

View File

@ -1,58 +0,0 @@
.section-buttons > a {
display: inline-block;
position: relative;
color: white;
background-color: darkslategray;
margin: 0.5em 0.2em;
padding: 0.75em 0;
opacity: 0.5;
}
.section-buttons > a:hover, .section-buttons > a[data-active="1"]:hover {
opacity: 0.8;
text-decoration: none;
}
.section-buttons > a[data-name="blog"] {
background-color: purple;
}
.section-buttons > a[data-name="works"] {
background-color: royalblue;
}
.section-buttons > a[data-name="album"] {
background-color: crimson;
background-image:
repeating-linear-gradient(
45deg, transparent
, transparent 2px, rgba(0,0,0,.2) 2px
, rgba(0,0,0,.2) 3px, transparent 3px
, transparent 5px, rgba(0,0,0,.2) 5px
);
}
.section-buttons > a[data-name="lifestyle"] {
text-shadow: 1px 1px 1px black;
background-image:
repeating-linear-gradient(
-15deg
, orangered 0%, orangered 16.6%
, lawngreen 16.6%, lawngreen 33.2%
, turquoise 33.2%, turquoise 49.8%
, darkorchid 49.8%, darkorchid 66.6%
, violetred 66.6%, violetred 83.3%
, royalblue 83.3%, royalblue
);
}
.section-buttons > a > span {
padding: 0.75em 0.5em;
}
.section-buttons > a[data-active="1"] {
opacity: 1;
}
.section-buttons > a > .count {
background-color: rgba( 0, 0, 0, 0.3 );
}

View File

@ -1 +0,0 @@
// __namespace( "Astro.Blog.Components.Section" );

View File

@ -1,17 +0,0 @@
.site-file {
max-width: 100%;
height: auto;
}
.sf_regular sup { vertical-align: baseline; }
.sf_regular {
padding: 1em;
background-color: #F0F0F0;
display: inline-block;
}
.sf_failed {
color: orangered;
opacity: 0.5;
}
.sf_failed:hover { opacity: 1; }

View File

@ -1,174 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components" );
/** @type {System.Debug} */
var debug = __import( "System.Debug" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
/** @type {Astro.Blog.Config} */
var Conf = __import( "Astro.Blog.Config" );
var getData = __import( "System.Net.getData" );
var getSMStamp = __import( "Astro.utils.Date.smstamp" );
/** @type {_AstConf_.SiteFile} */
var config = null;
var SiteFile = function ( id, hash, nObj )
{
if( !config ) throw new Error( "config is not defined" );
// TODO: Make a trigger for downloading from server
var stage = Dand.id( id );
if( !stage )
{
debug.Info( "[SiteFile] id not found: " + id );
return;
}
this.id = id;
this.hash = hash;
this.type = IDOMElement( stage ).getDAttribute( "type" );
if(!( this.type == "default" || this.type == null )) return this;
if( stage.getAttribute( "noauto" ) != null ) return this;
var applyStructure = function( obj )
{
return _applyStructure( JSON.parse( obj ).file );
};
var _applyStructure = function( obj )
{
/** @type {_AstJson_.SiteFile} */
var finfo = obj;
switch( finfo.type )
{
case "image":
var node = Dand.tag( "img", false, stage )[0];
switch( IDOMElement(stage).getDAttribute('size') )
{
case "small":
node.src = finfo.thumbs.small || ( config.path.image.small + hash + '.jpg' );
break;
case "medium":
node.src = finfo.thumbs.medium || ( config.path.image.medium + hash + '.jpg' );
break;
case "original":
node.src = config.path.image.original + hash + '.jpg';
break;
default: // large
node.src = finfo.thumbs.large || ( config.path.image.large + hash + '.jpg' );
}
stage.appendChild(Dand.wrapne(
'a', node
, [
new IKey( 'href', config.f_host + finfo.src_location )
, new IKey( 'title', finfo.name )
, new IKey( 'target', '_blank' )
]
));
break;
case "audio":
// TODO
break;
default:
// create a form to post hash string to php
var hash_field = Dand.wrapna(
'input', [ new IKey( 'type', 'hidden' ), new IKey( 'name', 'hash' ) ]
)
, name_field = Dand.wrapna(
'input', [ new IKey( 'type', 'hidden' ), new IKey( 'name', 'name' ) ]
)
, link = Dand.wrapne(
'a', 'download', new IKey( 'href', config.path.download + finfo.name )
)
, form = Dand.wrap(
'form', null, 'sf_regular'
, [ name_field, hash_field ]
, [
new IKey('target', '_blank')
, new IKey('action', config.path.download + finfo.name)
, new IKey('method', 'POST')
]
)
;
hash_field.value = hash;
name_field.value = finfo.name;
IDOMElement(link).addEventListener(
'Click'
, function(e) {
form.submit();
e.preventDefault();
return false;
}
);
// file name
form.appendChild( Dand.wrapne( 'span', 'File: ' + finfo.name) );
// download, submit button
form.appendChild( Dand.wrapne( 'sup', [ Dand.textNode(" ["), link, Dand.textNode("]") ] ) );
// hash
form.appendChild( Dand.wrapne( 'sup', Dand.wrape( 'MD5: ' + hash ) ) );
// date
form.appendChild( Dand.wrapne( 'sup', Dand.wrape( 'Date: ' + getSMStamp( new Date( finfo.date_created ) ) ) ) );
stage.appendChild(form);
}
};
var loadFailed = function( obj )
{
while( stage.hasChildNodes() ) stage.removeChild( stage.firstChild );
stage.appendChild( Dand.wrapc( "sf_failed", Dand.textNode( "Error: Failed to get resources info" ) ) );
};
if( nObj )
{
_applyStructure( nObj );
}
else
{
this.loadInfo( applyStructure, loadFailed );
}
};
SiteFile.prototype.loadInfo = function( success, failed )
{
getData( config.path.info + this.hash, success, failed );
};
var init = function()
{
config = Conf.get( "SiteFile" );
if( config )
{
var SFOs = Conf.get( "SFObjects" );
for( var i in SFOs )
{
var f = SFOs[i];
new SiteFile( f[0], f[1] );
}
}
};
Bootstrap.regInit( init );
ns[ NS_EXPORT ]( EX_CLASS, "SiteFile", SiteFile );
})();

View File

@ -1,8 +0,0 @@
.social_panel {
margin: 0.5em 0;
text-align: right;
}
.social_panel > div {
vertical-align: top;
}

View File

@ -1,40 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components.SocialButtons" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {System.utils.IKey} */
var IKey = __import( "System.utils.IKey" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
var init = function( id )
{
var s = Dand.tag( "script" )[0];
// Facebook
var fb = Dand.wrapna(
"script"
, IKey.quickDef(
"type" , 'text/javascript'
, "id" , 'facebook-jssdk'
, "src" , "//connect.facebook.net/en_US/all.js#xfbml=1"
)
);
// Google+
var gplus = Dand.wrapna(
"script"
, IKey.quickDef(
"type" , 'text/javascript'
, "async" , true
, "src" , "https://apis.google.com/js/plusone.js"
)
);
s.parentNode.insertBefore( fb, s );
s.parentNode.insertBefore( gplus, s );
};
Bootstrap.regInit( init );
})();

View File

@ -1,35 +0,0 @@
.spoiler {
}
.spoiler .title {
background: cornflowerblue;
color: white;
padding: 0.2em 0.5em;
cursor: default;
}
.spoiler .title:hover {
background: royalblue;
}
.spoiler .title[clicked] {
opacity: 0.8;
}
.spoiler .title:before {
padding-right: 0.5em;
content: "\25BC";
font-size: 0.75em;
}
.spoiler .title[clicked]:before {
content: "\25B2";
}
.spoiler .content {
padding: 0.5em;
font-size: 0.9em;
line-height: 1.2em;
background-color: rgba( 0, 0, 0, 0.02 );
display: none;
}

View File

@ -1,49 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components.Spoiler" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
/** @type {Astro.Blog.Config} */
var Config = __import( "Astro.Blog.Config" );
var Spoiler = function( id )
{
var sp_stage = Dand.id( "spoiler_" + id );
var sp_display = ( sp_stage.nodeName == "span" ) ? "inline-block" : "block";
var ostage = IDOMElement( sp_stage );
var sp_title = ostage.first( "DIV" );
var sp_content = ostage.last( "DIV" );
sp_title.onclick = function ()
{
var s_style = sp_content.style;
if( s_style.display == sp_display )
{
s_style.display = "none";
sp_title.removeAttribute( "clicked" );
}
else
{
s_style.display = sp_display;
sp_title.setAttribute( "clicked", "" );
}
};
sp_stage.hasAttribute( "expanded" ) && sp_title.onclick();
};
var sps = Config.get( "Spoiler" );
Bootstrap.regInit(function() {
for( var i in sps )
{
new Spoiler( sps[i] );
}
});
})();

View File

@ -1,24 +0,0 @@
.tag-ctrl .title {
font-size: 1.5em;
color: #444;
clear: both;
}
.tag-ctrl {
white-space-collapse: discard;
}
.tag-ctrl > div > div {
padding: 0.2em 0;
float: left;
}
.tag-ctrl > div > div > a {
padding: 0 0.2em;
}
.tag-ctrl > div > div > a:first-child:hover {
color: white;
background: purple;
text-decoration: none;
}

View File

@ -1 +0,0 @@
// __namespace( "Astro.Blog.Components.TagControl" );

View File

@ -1,46 +0,0 @@
.b_notify { background-color: #222 !important; }
.b_notify:before { content: 'Mute'; }
.b_notify:after { content: 'Notify'; }
.uc_ntoggle {
font-family: custom-sans;
vertical-align: top;
padding: 0.2em 0em;
}
.uc_ntoggle:before { content: '..'; }
.uc_ntoggle:after { content: '!'; }
.cr_ntoggle {
font-family: custom-sans;
padding: 0;
margin: 0;
position: absolute;
width: 1.5em;
height: 1.5em;
bottom: 0;
right: -3em;
border-radius: 2em 2em 2em 0em;
border: 0.5em solid white;
line-height: 1.5em !important;
background-color: white;
/* box-shadow: 2px 2px 10px -5px black; */
}
.cr_ntoggle:before, .cr_ntoggle:after {
padding: 0;
border-radius: 2em;
}
.cr_ntoggle:before {
content: '..';
background-color: orange;
}
.cr_ntoggle:after { content: '!'; }

View File

@ -1,35 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components.ToggleButton.CommentToggle" );
var ToggleButton = __import( "Astro.Blog.Components.ToggleButton" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
/** @type {Astro.Blog.Config} */
var Conf = __import( "Astro.Blog.Config" );
/** @type {_AstConf_.CommentToggle} */
var settings = Conf.get( "CommentToggle" );
var CommentToggle = function( id, processor, object )
{
ToggleButton.call( this, id, processor, object );
};
__extends( CommentToggle, ToggleButton );
var init = function()
{
for( var i in settings )
{
var button = settings[i];
new CommentToggle( button[0], button[1], button[2] );
}
}
Bootstrap.regInit( init );
})();

View File

@ -1,42 +0,0 @@
.b_button {
position: relative;
font-family: custom-sans;
font-size: 1em;
padding: 0.2em 0.5em;
margin: 0.5em 0.2em;
background-color: grey;
color: white;
cursor: default;
float: right;
}
.b_delete {
color: crimson;
background-color: crimson;
position: relative;
}
.b_delete:after {
content: "\2715";
color: white;
position: absolute;
width: 100%;
height: 100%;
text-align: center;
padding-top: 0.15em;
top: 0;
right: 0;
}
.b_delete:hover:after {
text-decoration: underline;
}
.b_scope { background-color: slategrey; }
.b_scope:before { content: 'Private'; background-color: purple; }
.b_scope:after { content: 'Public'; background-color: orangered; }

View File

@ -1,50 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components.ToggleButton.DeleteArticle" );
/** @type {Components.MessageBox} */
var MessageBox = __import( "Components.MessageBox" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
var postData = __import( "System.Net.postData" );
var init = function()
{
var aid = Dand.id( "b_entry", true ).getDAttribute( "aid" );
var stage = Dand.glass( "b_delete", true, Dand.id( "b_entry" ) );
if( !stage.length ) return;
stage = stage[0];
var doDelete = function( confirmed )
{
var a_deleteSuccess = function( args ) { window.location.reload( true ); };
var a_deleteFailed = function( args ) { };
if( confirmed ) postData(
"/ajax/del-article"
, { "article_id": aid }
, a_deleteSuccess
, a_deleteFailed
);
};
stage.addEventListener(
'Click'
, function (e) {
new MessageBox(
"Confirm"
, "Are you sure you want to delete this article?. Comments will also be deleted!"
, "Yes", "No"
, doDelete
).show();
}
);
};
Bootstrap.regInit( init );
})();

View File

@ -1,85 +0,0 @@
.btn_toggle {
position: relative;
font-family: serif;
font-size: 1em;
padding: 0.2em 0.5em;
margin: 0.5em 0.2em;
background-color: #222;
color: white;
cursor: default;
overflow: hidden;
display: inline-block;
opacity: 0.8;
}
.btn_toggle > .btn_space {
visibility: hidden;
padding: 0 0.5em;
}
.btn_toggle:hover {
opacity: 1;
text-decoration: none;
}
.btn_toggle:hover:before, .btn_toggle:hover:after {
text-decoration: underline;
}
.btn_toggle:before, .btn_toggle:after {
text-align: center;
position: absolute;
padding-top: 0.15em;
width: 100%;
height: 100%;
top: 0;
left: 0;
-webkit-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
-moz-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
-ms-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
-o-transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000);
transition-timing-function: cubic-bezier(0.215, 0.610, 0.355, 1.000); /* easeOutCubic */
}
.btn_toggle:before {
content: '';
top: 0%;
-webkit-transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-moz-transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-ms-transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-o-transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000); /* easeOutCubic */
}
.btn_toggle:after {
content: '';
background-color: #4169E1;
top: 100%;
-webkit-transition: all 750ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-moz-transition: all 750ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-ms-transition: all 750ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
-o-transition: all 750ms cubic-bezier(0.215, 0.610, 0.355, 1.000);
transition: all 500ms cubic-bezier(0.215, 0.610, 0.355, 1.000); /* easeOutCubic */
}
.btn_toggle[data-active="1"]:after {
top: 0%;
}
.btn_toggle[data-active="1"]:before {
top: -100%;
}

View File

@ -1,65 +0,0 @@
(function(){
var ns = __namespace( "Astro.Blog.Components" );
/** @type {Dandelion} */
var Dand = __import( "Dandelion" );
/** @type {Dandelion.IDOMElement} */
var IDOMElement = __import( "Dandelion.IDOMElement" );
/** @type {Astro.Bootstrap} */
var Bootstrap = __import( "Astro.Bootstrap" );
/** @type {Astro.Blog} */
var config = __import( "Astro.Blog.Config" );
/** @type {System.utils.DataKey} */
var DataKey = __import( "System.utils.DataKey" );
var postData = __import( "System.Net.postData" );
var ToggleButton = function ( elem, processor, obj )
{
var stage = Dand.id( elem, true );
if( !stage ) return;
var n_toggle = function (args)
{
if( stage.getDAttribute("active") == 1 )
{
stage.setAttribute( new DataKey( "active", 0 ) );
}
else
{
stage.setAttribute( new DataKey( "active", 1 ) );
}
};
var nError = function (args)
{
};
stage.addEventListener(
"Click"
, function (e) {
var _action = stage.getDAttribute( "active" ) == 1
? obj[ "disable" ]
: obj[ "enable" ]
;
postData( processor, _action, n_toggle, nError );
}
);
};
var init = function()
{
var toggles = config.get( "ToggleButtons" );
for( var i in toggles )
{
new ToggleButton( toggles[ i ][0], toggles[ i ][1], toggles[ i ][2] );
}
};
Bootstrap.regInit( init );
ns[ NS_EXPORT ]( EX_CLASS, "ToggleButton", ToggleButton );
})();

Some files were not shown because too many files have changed in this diff Show More