原文:对XAML进行编辑的辅助类(XamlHelper)

// XamlHelper.cs
// --------------------------------------------
// 对XAML进行编辑操作的辅助类:
// 对选中的XAML进行操作; 对XAML代码进行对齐整理; 对XAML标记进行着色显示等
// --------------------------------------------
using System;
using System.Collections.Generic;
using System.Text;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Collections;
using System.Windows;
using System.IO;
using System.Xml;
using System.Windows.Markup;

namespace BrawDraw.Com.Xaml.Utility
{

    /// <summary>
    /// Provides help functions for processing XAML.
    /// </summary>
    public class XamlHelper
    {
        /// <summary>
        /// Get XAML from TextRange.Xml property
        /// </summary>
        /// <param name="range">TextRange</param>
        /// <returns>return a string serialized from the TextRange</returns>
        public static string GetTextRangeXaml(TextRange range)
        {
            MemoryStream mstream;

            if (range == null)
            {
                throw new ArgumentNullException("range");
            }

            mstream = new MemoryStream();
            range.Save(mstream, DataFormats.Xaml);

            //must move the stream pointer to the beginning since range.save() will move it to the end.
            mstream.Seek(0, SeekOrigin.Begin);

            //Create a stream reader to read the xaml.
            StreamReader stringReader = new StreamReader(mstream);

            return stringReader.ReadToEnd();
        }

        /// <summary>
        /// Set XML to TextRange.Xml property.
        /// </summary>
        /// <param name="range">TextRange</param>
        /// <param name="xaml">XAML to be set</param>
        public static void SetTextRangeXaml(TextRange range, string xaml)
        {
            MemoryStream mstream;
            if (null == xaml)
            {
                throw new ArgumentNullException("xaml");
            }
            if (range == null)
            {
                throw new ArgumentNullException("range");
            }

            mstream = new MemoryStream();
            StreamWriter sWriter = new StreamWriter(mstream);

            mstream.Seek(0, SeekOrigin.Begin); //this line may not be needed.
            sWriter.Write(xaml);
            sWriter.Flush();

            //move the stream pointer to the beginning.
            mstream.Seek(0, SeekOrigin.Begin);

            range.Load(mstream, DataFormats.Xaml);
        }

        /// <summary>
        /// Parse a string to WPF object.
        /// </summary>
        /// <param name="str">string to be parsed</param>
        /// <returns>return an object</returns>
        public static object ParseXaml(string str)
        {
            MemoryStream ms = new MemoryStream(str.Length);
            StreamWriter sw = new StreamWriter(ms);
            sw.Write(str);
            sw.Flush();

            ms.Seek(0, SeekOrigin.Begin);

            ParserContext pc = new ParserContext();

            pc.BaseUri = new Uri(System.Environment.CurrentDirectory + "/");

            return XamlReader.Load(ms, pc);
        }

        public static string IndentXaml(string xaml)
        {
            //open the string as an XML node
            XmlDocument xmlDoc = new XmlDocument();
            xmlDoc.LoadXml(xaml);
            XmlNodeReader nodeReader = new XmlNodeReader(xmlDoc);

            //write it back onto a stringWriter
            System.IO.StringWriter stringWriter = new System.IO.StringWriter();
            System.Xml.XmlTextWriter xmlWriter = new System.Xml.XmlTextWriter(stringWriter);
            xmlWriter.Formatting = System.Xml.Formatting.Indented;
            xmlWriter.Indentation = 4;
            xmlWriter.IndentChar = ' ';
            xmlWriter.WriteNode(nodeReader, false);

            string result = stringWriter.ToString();
            xmlWriter.Close();

            return result;
        }

        public static string RemoveIndentation(string xaml)
        {
            if (xaml.Contains("/r/n    "))
            {
                return RemoveIndentation(xaml.Replace("/r/n    ", "/r/n"));
            }
            else
            {
                return xaml.Replace("/r/n", "");
            }
        }

        public static string ColoringXaml(string xaml)
        {
            string[] strs;
            string value = "";
            string s1, s2;
            s1 = "<Section xml:space=/"preserve/" xmlns=/"http://schemas.microsoft.com/winfx/2006/xaml/presentation/"><Paragraph>";
            s2 = "</Paragraph></Section>";

            strs = xaml.Split(new char[] { '<' });
            for (int i = 1; i < strs.Length; i++)
            {
                value += ProcessEachTag(strs[i]);
            }
            return s1 + value + s2;
        }

        static string ProcessEachTag(string str)
        {
            string front = "<Run Foreground=/"Blue/">&lt;</Run>";
            string end = "<Run Foreground=/"Blue/">&gt;</Run>";
            string frontWithSlash = "<Run Foreground=/"Blue/">&lt;/</Run>";
            string endWithSlash = "<Run Foreground=/"Blue/"> /&gt;</Run>";//a space is added.
            string tagNameStart = "<Run FontWeight=/"Bold/">";
            string propertynameStart = "<Run Foreground=/"Red/">";
            string propertyValueStart = "/"<Run Foreground=/"Blue/">";
            string endRun = "</Run>";
            string returnValue;
            string[] strs;
            int i = 0;

            if (str.StartsWith("/"))
            {   //if the tag is an end tag, remove the "/"
                returnValue = frontWithSlash;
                str = str.Substring(1).TrimStart();
            }
            else
            {
                returnValue = front;
            }
            strs = str.Split(new char[] { '>' });
            str = strs[0];
            i = (str.EndsWith("/")) ? 1 : 0;

            str = str.Substring(0, str.Length - i).Trim();

            if (str.Contains("="))//the tag has a property
            {
                //set tagName
                returnValue += tagNameStart + str.Substring(0, str.IndexOf(" ")) + endRun + " ";
                str = str.Substring(str.IndexOf(" ")).Trim();
            }
            else //no property
            {
                returnValue += tagNameStart + str.Trim() + endRun + " ";
                //nothing left to parse
                str = "";
            }

            //Take care of properties:
            while (str.Length > 0)
            {
                returnValue += propertynameStart + str.Substring(0, str.IndexOf("=")) + endRun + "=";
                str = str.Substring(str.IndexOf("/"") + 1).Trim();
                returnValue += propertyValueStart + str.Substring(0, str.IndexOf("/"")) + endRun + "/" ";
                str = str.Substring(str.IndexOf("/"") + 1).Trim();
            }

            if (returnValue.EndsWith(" "))
            {
                returnValue = returnValue.Substring(0, returnValue.Length - 1);
            }

            returnValue += (i == 1) ? endWithSlash : end;

            //Add the content after the ">"
            returnValue += strs[1];

            return returnValue;
        }
    }
}
 

对XAML进行编辑的辅助类(XamlHelper)的更多相关文章

  1. wpf xaml文件编辑出现中文乱码

    突然有一天,发现在xaml文件编辑窗里打汉字出来了乱码...抓狂 结果发现是番茄助手搞得鬼.只能在编辑xaml文件是暂时关闭番茄助手 visual assist

  2. WPF入门教程系列十九——ListView示例(一)

    经过前面的学习,今天我做一个比较综合的WPF程序示例,主要包括以下功能: 1) 查询功能.从数据库(本地数据库(local)/Test中的S_City表中读取城市信息数据,然后展示到WPF的Windo ...

  3. WPF 杂谈——入门介绍

    对于WPF的技术笔者是又爱又恨.现在WPF的市场并不是很锦气.如果以WPF来吃饭的话,只怕会饿死在街头.同时现在向面WEB开发更是如火冲天.所以如果是新生的话,最好不要以WPF为主.做为选择性来学习一 ...

  4. Blend 2015 教程 (五) 自定义状态

    本篇再补充一块内容,就是自定义状态的介绍. 自定义状态用于封装用户控件在各种状态之间切换时的外观变化及其动画效果,方便调用.比如有个用户控件用于实现类似舞台幕布打开和关闭切换的效果,可以创建幕布关闭和 ...

  5. UWP 播放媒体控件

    最近我的uwp需要有一个有声朗读的功能,like this 点击声音按钮就可以有声朗读了.这里主要是用了媒体播放的控件. 一般我们把需求分为两种: 一种是不需要呈现播放器的样子,只需要用户点击一下别的 ...

  6. WPF实用指南一:在WPF窗体的边框中添加搜索框和按钮

    原文:WPF实用指南一:在WPF窗体的边框中添加搜索框和按钮 在边框中加入一些元素,在应用程序的界面设计中,已经开始流行起来.特别是在浏览器(Crome,IE,Firefox,Opera)中都有应用. ...

  7. [MAUI] 在.NET MAUI中结合Vue实现混合开发

    ​ 在MAUI微软的官方方案是使用Blazor开发,但是当前市场大多数的Web项目使用Vue,React等技术构建,如果我们没法绕过已经积累的技术,用Blazor重写整个项目并不现实. Vue是当前流 ...

  8. VS编程,编辑WPF过程中,点击设计器中界面某一控件,在XAML中高亮突出显示相应的控件代码的设置方法。

    原文:VS编程,编辑WPF过程中,点击设计器中界面某一控件,在XAML中高亮突出显示相应的控件代码的设置方法. 版权声明:我不生产代码,我只是代码的搬运工. https://blog.csdn.net ...

  9. vs.net2017在编辑的wpf的xaml文件引用本程序集下的类提示“找不到”

    local对应就是当前exe程序下的类,会提示“...命令空间...找不到...” 因为我调整过生成的,于是尝试调回来anyCPU 问题解决. 看了一下vs.net2017的所在目录"C:\ ...

随机推荐

  1. [CSS] Use CSS Counters to Create Pure CSS Dynamic Lists

    CSS counters let you create dynamic lists without JavaScript. In this lesson, we will create a multi ...

  2. iOS8新特性

    1. App Extension Programming Guide 2.LocalAuthentication.framework - Touch ID Authentication 3.Local ...

  3. 可视化格式模型(visual formatting model)

    原文 简书原文:https://www.jianshu.com/p/7632f16ff555 大纲 1.认识可视化模型 2.可视化模型的内容 3.可视化模型的影响因素 1.认识可视化模型 盒子模型是C ...

  4. 使用XX-Net永久访问真正的互联网

    XX-Net基于GoAgent(代理软件),使用谷歌App Engine(GAE)代理服务器通过防火墙,是github上的一个开源项目. https://github.com/XX-net/XX-Ne ...

  5. 《SPA设计与架构》之客户端路由

    原文 简书原文:https://www.jianshu.com/p/4d83475f71da 大纲 1.传统路由 2.SPA导航 3.客户端路由器的工作机制 1.传统路由 在传统Web应用程序中,导航 ...

  6. 从Ecipse中导出程序至apk 分类: H1_ANDROID 2013-10-26 22:17 516人阅读 评论(0) 收藏

    若未有数字证书: 1. 2. 3. 4. 5. 若已有数字证书: 上面的后3步改为 版权声明:本文为博主原创文章,未经博主允许不得转载.

  7. 【54.08%】【BZOJ 1941】Hide and Seek

    Time Limit: 16 Sec  Memory Limit: 162 MB Submit: 919  Solved: 497 [Submit][Status][Discuss] Descript ...

  8. js进阶 11-2 jquery属性如何操作

    js进阶 11-2  jquery属性如何操作 一.总结 一句话总结:jquery中的属性用attr方法表示.jquery中都是方法. 1.jquery中的属性的增删改查操作? 只需要两个方法, at ...

  9. Android推送进阶课程学习笔记

    今天在慕课网学习了Android进阶课程推送的server端处理回执的消息 . 这集课程主要介绍了,当server往client推送消息的时候,client须要发送一个回执回来确认收到了推送消息才算一 ...

  10. [TFS4]TFS git地址,分支概念

    1)上传本地代码到TFS a.Generate Git Credentials,即创建git账户密码 b)上传本地代码 git add *git commit -m "纳入管理" ...