我正在为asp.net
网络表单应用程序使用dotnetless(http://www.dotlesscss.org/),它运行良好。我喜欢使用颜色,字体大小等变量。但我可以看到变量值是静态的。
有没有办法使用dotnetless根据用户标识从数据库初始化这些变量值?
基本上我想将这个Web应用程序转换为基于主题的网站,因此每个用户都可以选择自己的颜色,字体,字体大小等。
任何方向都将受到高度赞赏。
答案 0 :(得分:5)
这绝对是可能的,但不幸的是你不能从LESS本身查询你的数据库,所以你基本上需要为用户编写LESS文件并使用所需的变量值,然后加载它。
您可以在此处找到另一个答案的示例:https://stackoverflow.com/a/11628325/2330244
答案 1 :(得分:5)
我认为如果这是你想要的路径,你应该创建一个IHttpHandler来替换无点的LessCssHttpHandler。此处理程序将执行与LessCssHttpHandler基本相同的操作,但会在编译成css之前将数据库变量插入到较少的数据库中。
您可以查看使用无点进行较少翻译的Bundle Transformer LESS项目。它还有一个IHttpHandler,你可以将它作为你的基础。
正如其他人所说,这可能不是最好的行动方案
修改强> 处理程序的基本起点
public class LessHandler : IHttpHandler
{
public void ProcessRequest(HttpContext context)
{
var request = context.Request;
var response = context.Response;
var user = context.User;
string assetUrl = request.Url.LocalPath;
string assetPath = context.Server.MapPath(assetUrl);
//load less file into the data.
var data = "";
using (var file = new StreamReader(assetPath))
{
data = file.ReadToEnd();
}
DotlessConfiguration lessEngineConfig = DotlessConfiguration.GetDefault();
lessEngineConfig.MapPathsToWeb = false;
lessEngineConfig.CacheEnabled = false;
lessEngineConfig.DisableUrlRewriting = false;
lessEngineConfig.Web = false;
lessEngineConfig.MinifyOutput = true;
lessEngineConfig.LessSource = typeof(VirtualFileReader);
var lessEngineFactory = new EngineFactory(lessEngineConfig);
ILessEngine lessEngine = lessEngineFactory.GetEngine();
string vars = "";
//TODO set default for vars
if (user != null)
{
//TODO get vars for user
}
var content = lessEngine.TransformToCss(string.Format("{0}{1}", vars, data), null);
// Output text content of asset
response.ContentType = "text/css";
response.Write(content);
response.End();
}
public bool IsReusable
{
get { return true; }
}
}
答案 2 :(得分:5)
为什么不创建一个带有函数的自定义.LESS插件来执行所需的查找?
下面的代码是测试,如图所示。我实际上并没有在数据库中查找数据,但是所有必要的信息都应该可用。我确认在网站上以Windows身份验证模式运行时,我能够通过HttpContext.Current.User.Identity.Name
检索当前用户。
要使用下面的功能,您可以在较少的文件中输入以下内容:
--lookup using custom function (hit db)
@brand_color:getCustomColor(usersThemeAttribute);
--then use the variable like normal
color: @brand_color;
<强>代码强>
[DisplayName("UserProfilePlugin")]
public class UserProfilePlugin : IFunctionPlugin
{
public Dictionary<string, Type> GetFunctions()
{
return new Dictionary<string, Type>
{
{ "getCustomColor", typeof(GetCustomColorFunction) }
};
}
}
public class GetCustomColorFunction : Function
{
protected override Node Evaluate(Env env)
{
Guard.ExpectNumArguments(1, Arguments.Count(), this, Location);
Guard.ExpectNode<Keyword>(Arguments[0], this, Arguments[0].Location);
//the idea is that you would have many colors in a theme, this would be the name for a given color like 'bgColor', or 'foreColor'
var colorAttrName = Arguments[0] as Keyword;
//Lookup username
// string username = HttpContext.Current.User.Identity.Name;
//perform some kind of DB lookup using the username, get user theme info
// UserProfile up = new UserProfile();
// System.Drawing.Color c = up.GetColorByAttribute(colorAttrName.Value);
//return the appropriate color using RGB/etc...
// return new Color(c.R, c.G, c.B);
return new Color(129, 129, 129);
}
}
要注册插件,请将此添加到web.config:
<dotless cache="false" >
<plugin name="UserProfilePlugin" assembly="Your.Assebly.Name" />
</dotless>
考虑禁用无线缓存,以便更改用户立即生效。
答案 3 :(得分:2)
最简单的解决方案可能是在您的网页中内联您的LESS代码:(如here所述)
<html>
<head>
<style type="text/less">
// DB and user-dependent code here
</style>
</head>
...
</html>
这样,您可以像自定义网页一样自定义LESS样式表。
如果您想使用无点编译的CSS,您可以将自定义样式表传递给无点解析器:
Less.Parse(".foo { font-size: <user-dependent-value>;}")
然后,您需要将编译的CSS输出直接包含在您的网页中:
<html>
<head>
<style type="text/css">
// result of Less.Parse(...)
</style>
</head>
...
</html>
答案 4 :(得分:1)
这取决于你将拥有多少主题。如果您的数量有限,那么将用户映射到您预先编译的.less主题之一是最好的(无论是性能还是复杂性)。
但是如果你允许每个用户自定义主题以便有很多(或无限数量)主题,那么当主题是主题时,最好构造,编译,优化.less(或CSS)文件。更改并保存结果。在每个页面加载时,您引用该主题文件,直到用户选择新主题。最好的情况是,它会长时间缓存在用户的系统上。
除非是少量的自定义LESS / CSS,否则我会避免内联CSS路由。它会增加每个页面的文件大小/带宽,因此在移动设备上加载速度会更慢。相反,我会使用最近的ASP.NET Web.Optimization包来帮助您构建,编译和优化LESS - &gt;主题更改时的CSS并缓存结果。
因此,在页面加载时,大多数页面将引用保存在数据库中的现有自定义页面主题。在主题更改后,您将完全减少 - &gt; css过程。