sábado, 27 de junio de 2015

Error en los espacios de reunión de SharePoint: 'g_InstanceID' no esta definido

Jugando con las páginas maestras en SharePoint, descubrí que al volver a aplicar la default.master, a un sitio que tuviera como subsitio un espacio de reuniones, me genero un error de Javascript que me decía que 'g_InstanceID' no esta definido y me impedía que al hacer clic en las fechas de la parte izquierda, pudiera ver el contenido de los documentos asociados a dicha fecha:


Para solucionar esto, basta con hacer una copia de la página maestra, en nuestro caso default.master, renombrarla y añadir tras la etiqueta <%@ Import Namespace=”Microsoft.SharePoint” %>:


<%@ Register Tagprefix="Meetings" Namespace="Microsoft.SharePoint.Meetings" 
Assembly="Microsoft.SharePoint, Version=12.0.0.0, Culture=neutral, 
PublicKeyToken=71e9bce111e9429c" %>

Y tras la apertura de la etiqueta de <body> añadiremos:

<Meetings:PropertyBag runat="server"/>

Guardaremos la nueva pagina maestra, la publicaremos y la aplicaremos a nuestro espacio de reuniones y veremos como el problema se ha solucionado.

Fuente: http://sympmarc.com/2008/07/02/how-to-fix-recurring-meeting-workspace-error-%E2%80%98g_instanceid%E2%80%99-is-undefined/

sábado, 16 de mayo de 2015

Imagen aleatoria

Hoy un cliente me ha pedido que quería una foto aleatoria en el portal. Diferente para cada vez que accediera al portal.

La solución ha sido fácil.

Primero he creado una Biblioteca de Imágenes. En ella una columna de o No, con valor por defecto a . Que nos servirá para que el propio usuario elija entre que fotos quiere que se haga la selección sin tener que eliminarlas de la biblioteca. Sólo tendrá que marcarlas a No.

Lo siguiente ha consistido en hacer una Vista de Datos, en la que mostramos todos los elementos y filtramos por los que el campo anterior esta a Sí. SharePoint Designer generará todo el código por nosotros. Veremos que tenemos todas las fotos en una tabla, una debajo de otra.

Ahora entraremos en código y buscaremos:

<xsl:template name="dvt_1">
<xsl:variable name="dvt_StyleName">Table</xsl:variable>
<xsl:variable name="Rows" select="/dsQueryResponse/Rows/Row"/>

Y añadiremos la siguiente lineas tras lo anterior:

<xsl:variable name="totalRows" select="count($Rows)" />

Quedando:

<xsl:template name="dvt_1">
<xsl:variable name="dvt_StyleName">Table</xsl:variable>
<xsl:variable name="Rows" select="/dsQueryResponse/Rows/Row"/> <xsl:variable name="totalRows" select="count($Rows)" />

Lo único que hemos hecho, es recoger en totalRows, el número de imágenes que están marcadas a .
Buscaremos la llamada al Body:

<xsl:call-template name="dvt_1.body">

Y justo antes de él, crearemos nuestro número aleatorio y los guardaremos en una variable:

<xsl:variable name="RandomNumber" select="ddwrt:Random(1, $totalRows)" />

Ya tenemos lo más importante, nuestro número aleatorio, entre 1 y el número de imágenes totales con la columna marcada a . Y se las pasaremos como parámetro a dvt_1.body. Quedando el código:

<xsl:variable name="RandomNumber" select="ddwrt:Random(1, $totalRows)" />
<xsl:call-template name="dvt_1.body">
<xsl:with-param name="Rows" select="$Rows"/>
<xsl:with-param name="RandomNumber" select="$RandomNumber"/>
</xsl:call-template>

Dentro de dvt_1.body recogeremos el valor de RandomNumbre y se lo pasaremos a la función dvt_1.rowview que es la que pinta cada uno de los elementos por medio de un for-each, quedando:

<xsl:template name="dvt_1.body">
<xsl:param name="Rows"/>
<xsl:param name="RandomNumber"/>
<xsl:for-each select="$Rows">
<xsl:call-template name="dvt_1.rowview">
<xsl:with-param name="RandomNumber" select="$RandomNumber"/>
</xsl:call-template>
</xsl:for-each>
</xsl:template>

Y por último, dentro de dvt_1.rowview, recogeremos el valor de RandomNumber y por medio de un if, pintaremos sólo el elemento (@ID) que coincida con nuestro número aleatorio. Quedando:

<xsl:template name="dvt_1.rowview">
<xsl:param name="RandomNumber"/>
<xsl:if test="@ID = $RandomNumber">
<tr>
                                <td>
                                     <img border="0" src="{@FileRef}"/>
</td>
                        </tr>
</xsl:if>
</xsl:template>

La maquetación ya corre por cuenta de cada uno. En mi caso, debía ocupar el 100% de la página y tener un borde negro.

Esta vez no he buscado en San Google, sino que como tenía poco trabajo, lo he creado pensando un poquito. Como se puede ver, no ha sido muy complicado, aunque estoy seguro, que si buscáis, habrá mil maneras de hacerlo.


sábado, 25 de abril de 2015

Obtener parámetros de la URL

Constantemente utilizamos la URL para pasar parámetros cuando estamos trabajando con SharePoint. De hecho el propio SharePoint es el primero que lo hace y el caso más fácil de ver, es cuando accedemos a un elemento de lista, ya sea en forma de edición o de presentación:

http://misitoweb/Lists/Alertas/EditForm.aspx?ID=39&Source=http%3A%2F%2Fmisitioweb%2FLists%2FAlertas%2FAllItems%2Easpx

En este ejemplo, podemos ver que tenemos dos parámetros ID y Source, que sirven para identificar el elemento y a dónde nos va a llevar una vez aceptemos o cancelemos la edición del elemento.

Normalmente para obtener y tratarlo, utilizaríamos JavaScript y/o JQuery, y trataríamos la URL.

La idea que propongo en esta entrada es encapsular una función que ya nos lo obtenga y que incluyéndola en un archivo .js, nos permitiría referenciarla en la página maestra y utilizar en nuestro portal.

El código sería sencillo:

function getUrlVars() {
  var vars = {};
  var parts = window.location.href.replace(/[?&]+([^=&]+)=([^&]*)/gi, function(m,key,value) {
    vars[key] = value;
  });
  return vars;
}


Esto nos permitiría recuperar dicho parámetro haciendo algo tan sencillo como:

var elemento = getUrlVars()["ID"];
var destino = getUrlVars()["Source"];

Y poder trabajar con ellas. Como se ve, es algo fácil y sencillo.

La idea la obtuve de:
http://papermashup.com/read-url-get-variables-withjavascript/

miércoles, 18 de marzo de 2015

Otra manera de abrir en nueva ventana en una vista de datos

Buscando por internet como abrir documentos en otra ventana, encontré una manera curiosa:

<script src="https://ajax.microsoft.com/ajax/jquery/jquery-1.3.2.min.js" type="text/javascript"></script>
<script type="text/javascript">
$(document).ready(function() {
  $("a[href$='#openinnewwindow']").each(function() {
    $(this).attr("target", "_blank");
    $(this).attr("href", $(this).attr("href").replace(/#openinnewwindow/, ''));
  });
});
</script>


Traducido significa, que en una vista de datos, en una consulta de contenido o en un resultado de búsqueda, todos los enlaces que yo quiera que se abran en nueva ventana, basta con que los marque con id="openinnewwindow" y este código que puede ir en la página maestra, en un archivo js referenciado o directamente en un editor de contenido, hará que busque todos estos elementos, les ponga un target="_blank" y elimine del id el valor openinnewwindow reemplazándolo por ''.

Fácil y sencillo.

 La página donde encontré esta curiosa propuesta es:
http://blog.scoreman.net/2010/10/open-sharepoint-links-in-new-window-using-jquery/

sábado, 21 de febrero de 2015

Abrir PDF's en nueva ventana

En uno de los clientes, me han pedido que los PDF no se abrieran en el navegador.

Esto les supone un problema porque al cerrar el PDF, suelen cerrar el navegador y luego tiene que volver a entrar.

Para resolver este problema, en la configuración avanzada de la biblioteca, existe la posibilidad de abrir los documentos en la aplicación nativa:


Pero en nuestro caso, esto no funciona porque en la configuración del propio Adobe Reader, tienen marcado que se abra en el navegador. Cambiar esto les supone un gran trastorno dentro de la empresa, así que tome la opción de hacerlo vía JQuery:

<script src="http://ajax.googleapis.com/ajax/libs/jquery/1.11.2/jquery.min.js"></script>
<script>

/*Que se ejecute cuando ya se haya cargado toda la página*/
$(document).ready(function(){

     /*Buscamos todos los documentos que acaben en .pdf*/
    $('[href$=".pdf"]').each(function(){ 

        /*Vacio el onclick que suele traer*/    
       $(this).attr('onclick','');

        /*Y le pongo el atributo target="_blank"*/
       $(this).attr('target','_blank');
    });
});
</script>


Incluyendo dicho código en la pagina maestra, ya lo tendríamos disponible para toda la colección de sitios.

Fácil y sencillo. Y el cliente ha quedo contento.

miércoles, 21 de enero de 2015

Imprimir una zona de una vista de datos

Uno de los clientes para los que trabajo, pidió que hiciera una vista de datos en la que salían unas peticiones mensuales. Hasta aquí, nada nuevo.

Lo siguiente que se le ocurrió, era que quería imprimirse esa vista de datos. Para ello, ni corto, ni perezoso, le propuse que diera a imprimir desde el navegador.

Esa solución, como no podía ser de otra manera, no le gusto. Quería imprimir sólo los datos, pero que no saliera la URL, ni partes del portal, sólo los datos.

Para ello, decidimos hacerlo con jquery, para ello en el table que se crea antes de recorrer todos los valores:

<table border="0" width="100%" cellpadding="2" cellspacing="0">
<tr valign="top">
<xsl:if test="$dvt_1_automode = '1'" ddwrt:cf_ignore="1">
<th class="ms-vh" width="1%" nowrap="nowrap"></th>
</xsl:if>
<th class="ms-vh" nowrap="nowrap">Título</th>
<th class="ms-vh" nowrap="nowrap">Cuerpo</th>
<th class="ms-vh" nowrap="nowrap">Caduca</th>
</tr>
       <xsl:call-template name="dvt_1.body">
<xsl:with-param name="Rows" select="$Rows"/>
<xsl:with-param name="FirstRow" select="1" />
<xsl:with-param name="LastRow" select="$dvt_RowCount" />
</xsl:call-template>
</table>

Lo que haremos será ponerle un class="ZonaImprimible" quedando:
<table border="0" width="100%" cellpadding="2" cellspacing="0" class="ZonaImprimible">

Esto nos servirá para definir que parte será la que imprimiremos, en este caso todo el table.
Tras la tabla, pondremos un botón que nos sirva para imprimir:
</table>
<p><input type="button" class="Impresora" value="Imprimir"/></p>

Y por último, pondremos la referencia a jquery y los archivos que necesitamos. El código que nos hará que se imprima sólo la tabla será:
<script src="/PruebasVarias/Biblioteca/jquery-1.10.2.js"></script>
<script src="/PruebasVarias/Biblioteca/jquery-ui-1.10.4.custom.js"></script>
<script src="/PruebasVarias/Biblioteca/jquery.PrintArea.js"></script>

<script type="text/javascript">
$(document).ready(function() {
   $(".Impresora").bind("click",function() {
       $(."ZonaImprimible").printArea(mode : "popup", popClose : true);
   });
});

</script>

Esto hará que se nos imprima sólo la tabla y que veamos en un popup lo que vamos a imprimir.
Es importante tener en cuenta, que si no metemos la hoja de estilos dentro de la zona a imprimir, lo que imprimiremos será sólo texto plano.

Para más información y más posibilidades, se puede consultar:
https://plugins.jquery.com/PrintArea/
http://www.jqueryscript.net/other/Print-Specified-Area-Of-A-Page-PrintArea.HTML

Como siempre, tome la idea de:
http://www.martiniglesias.eu/blog/imprimir-un-area-determinada-del-documento-con-jquery/207

viernes, 19 de diciembre de 2014

Cómo editar una página de SharePoint que aparece la edición deshabilitada

En un cliente, que trabaja con un SharePoint 2007, he detectado que la master tiene errores de código, producidos al intentar personalizarla.

Eso ha dado como resultado, que al intentar editar la página de inicio, he visto que la opción Editar página, que sale del menú de Acciones de sitio, aparece deshabilitada.

Necesitaba agregar una nueva lista a una Zona de Elementos Web. Así que buscando por internet, he encontrado una solución, que consiste en añadir a la URL el parámetro "?ToolPaneView=2".

En caso de que en la URL ya aparezca algún parámetro, como por ejemplo:
http://misitio/default.aspx?ID=12

Lo que deberíamos hacer es añadirlo como "&ToolPaneView=2".

La idea la encontré en:
http://davidandrewsmith.us/2009/09/11/edit-page-option-greyed-out-or-missing-or-disabled/